精华内容
下载资源
问答
  • 什么是耦合性和内聚性?

    千次阅读 2020-04-18 19:26:24
    仔细通读这篇文章,你就能理解耦合性和内聚性的概念与关系。 WHY? Why?如果你使用过面向对象的编程语言,初学者很容易: 把所有代码都写到一个方法里。 当我翻回到我曾经写过的代码后,我绝望了。 比如我们要获取一...

    前言

    如果你涉及软件开发,可能会经常听到“高内聚,低耦合”这种概念型词语。我在第一次接触这种词语时,也抱有很大的疑问,但我发现百度上大部分都是高大上的词汇解释。

    仔细通读这篇文章,你就能理解耦合性和内聚性的概念与关系。

    WHY?

    Why?如果你使用过面向对象的编程语言,初学者很容易:

    把所有代码都写到一个方法里。

    当我翻回到我曾经写过的代码后,我绝望了。

    比如我们要获取一个用户的信息,我们需要先:

    1. 在代码中填写数据库的地址、用户名、密码、表名
    2. 加载SQL驱动
    3. 执行语句
    4. 获得结果
    

    如果你只需要在一个方法里调用用户的信息,你可以把这四步的代码全部写到那个方法中。

    但是如果我们有多个方法都要调用数据库呢?

    把这段语句写四五六七八九遍?

    不不不。不但你会抓耳挠腮,IDE都看不下去了。

    如果我们新建一个方法,专门用于读取用户的信息呢?

    在这个方法中,是上方执行语句的代码,但不同的是,我们使用其它方法调用该查询方法的时候,传入查询语句,这个方法就能返回给我们想要的值。

    你只要将查询代码单独写成一个方法,当其它方法需要查询的时候,只需要调用这个查询方法并传入想查询的数据就可以了。

    DO!

    由于我不会用其它语言,所以这里使用Java进行演示。

    首先看下面这串代码:

    public class SimpleDemo {
        //由姓名获取某个用户的全部信息
        public void byName() {
            //1.创建驱动程序类对象
            Driver driver = new com.mysql.jdbc.Driver();
     
            //设置用户名和密码
            Properties props = new Properties();
            props.setProperty("user", "root");
            props.setProperty("password", "toor");
     
            //2.连接数据库,返回连接对象
            Connection conn = driver.connect(url, props);
     
            String sql="select * from users where name = 'lilei'";
            Statement pstmt = conn.createStatement();
            ResultSet rs=pstmt.executeQuery(sql);
            
            System.out.println("结果为:" + rs.next());
        }
        
        //由ID获取某个用户的全部信息
        public void byID() {
            //1.创建驱动程序类对象
            Driver driver = new com.mysql.jdbc.Driver();
     
            //设置用户名和密码
            Properties props = new Properties();
            props.setProperty("user", "root");
            props.setProperty("password", "toor");
     
            //2.连接数据库,返回连接对象
            Connection conn = driver.connect(url, props);
     
            String sql="select * from users where id = 1";
            Statement pstmt = conn.createStatement();
            ResultSet rs=pstmt.executeQuery(sql);
     
            System.out.println("结果为:" + rs.next());
        }
        
        //由年龄获取某个用户的全部信息
        public void byAge() {
            //1.创建驱动程序类对象
            Driver driver = new com.mysql.jdbc.Driver();
     
            //设置用户名和密码
            Properties props = new Properties();
            props.setProperty("user", "root");
            props.setProperty("password", "toor");
     
            //2.连接数据库,返回连接对象
            Connection conn = driver.connect(url, props);
     
            String sql="select * from users where age = 18";
            Statement pstmt = conn.createStatement();
            ResultSet rs=pstmt.executeQuery(sql);
     
            System.out.println("结果为:" + rs.next());
        }
    
    }
    

    我们使用用户名、ID、年龄读取了三次信息,你会发现一件事:

    重复的代码太多!

    如果我们稍加修改:

    public class SimpleDemo {
        //执行数据库语句
        public ResultSet doSQL(String sql) {
            //1.创建驱动程序类对象
            Driver driver = new com.mysql.jdbc.Driver();
     
            //设置用户名和密码
            Properties props = new Properties();
            props.setProperty("user", "root");
            props.setProperty("password", "toor");
     
            //2.连接数据库,返回连接对象
            Connection conn = driver.connect(url, props);
            Statement pstmt = conn.createStatement();
            ResultSet rs=pstmt.executeQuery(sql);
     
            return rs;
        }
     
        public void byName() {
            ResultSet rs = doSQL("select * from users where name = 'lilei'");
            System.out.println("结果为:" + rs.next());
        }
     
        public void byID() {
            ResultSet rs = doSQL("select * from users where id = 1");
            System.out.println("结果为:" + rs.next());
        }
     
        public void byAge() {
            ResultSet rs = doSQL("select * from users where age = 18");
            System.out.println("结果为:" + rs.next());
        }
    
    }
    

    利用传值,我们将大部分冗余代码进行了清理。
    后语
    概念

    讲了这么多,你大概猜到耦合是什么意思了:

    将一串代码模块化(即封装为不同方法),每个模块(方法)都有自己的功能。
    封装方法越多,耦合度越低。模块与模块之间接口的复杂程度和联系越复杂,
    耦合度越高。
    

    那么内聚就是:

    每个模块(方法)相互分离的情况下,修改了某模块(方法)其中的某些代码,
    但并不影响和其它模块的通讯(即高内聚)。每个模块尽可能独立完成自己的功能,
    不依赖于模块外部的代码。
    

    总结

    “高内聚,低耦合”是面向对象编程的基本原则,
    我们能获得更好的维护性和更佳的可读性。
    

    如转载请在文章尾部添加:

     原作者来自AdlerED个人技术博客:https://www.stackoverflow.wiki/
    
    展开全文
  • 模块独立的度量(耦合度和内聚度)

    千次阅读 2020-11-21 22:28:16
    从两个方面来度量模块之间的独立,这两个概念是模块的耦合度和模块的内聚度 耦合度 耦合度分为: 独立耦合 , 数据耦合 , 控制耦合 , 公共耦合 和 内容耦合 独立耦合 指两个模块之间彼此完全独立,没有直接联系,他们...

    模块独立性的度量

    从两个方面来度量模块之间的独立性,这两个概念是模块的耦合度和模块的内聚度

    耦合度

    耦合度分为: 独立耦合 , 数据耦合 , 控制耦合 , 公共耦合 和 内容耦合

    独立耦合

    指两个模块之间彼此完全独立,没有直接联系,他们之间的联系仅仅在于他们同属于一个软件系统或共有一个上层模块,这是耦合程度最低的一种(系统中不可能所有的模块都属于这种关系)

    数据耦合

    数据耦合指两个模块彼此交换数据,如: 一个模块的输出数据是另一个模块的输入数据,或者一个模块带参数调用另一个模块,下层模块又返回参数,在一个系统中,这种耦合是不可避免的,数据耦合的联系程度也较低,这种耦合是不可避免的

    控制耦合

    在调用过程中,若两个模块间传递的不是数据而是控制参数,则模块间的关系为控制耦合,控制耦合不是一种必须存在的耦合
    当被调用模块收到控制信息作为输入参数时,说明该模块内部存在多个并列的逻辑路径,即有多个功能,控制变量从多个功能中选择所要执行的部分,控制耦合是可以完全避免的

    • 找出模块调用时所用的一个或多个控制变量
    • 在被调模块中根据控制变量找出所有的流程
    • 将每一个流程分解为一个独立的模块
    • 将原被调模块中的流程选择部分移到上层模块,变为调用判断

    公共耦合

    公共耦合又称为公共环境耦合或者数据区耦合,如果多个模块对同一个数据区进行存取操作,则它们之间的关系就是公共耦合,公共耦合最弱的一种是:两个模块共享一个数据变量,一个模块只向其中写数据,另一个模块只从其中读数据
    注意的是: 公共耦合很强的时候,关系会变得错综负责,难以控制,系统的可靠性下降,可理解性,可维护性变差

    内容耦合

    内容耦合是耦合程序最高的一种形式,若一个模块直接访问另一个模块的内部代码或数据,即出现内容耦合,内容耦合会严重破坏模块的独立性和系统的结构化,代码相互纠缠,运行错综复杂,应尽量避免
    内容耦合往往变现为以下几种形式:

    • 一个模块访问另一个模块的内部代码或数据
    • 一个模块不通过正常入口而转到另一个模块的内部(如使用goto语句或者jmp指令直接进入另一个模块的内部)
    • 两个模块有一部分代码重叠
    • 一个模块有多个入口(这意味着一个模块有多种功能)
      模块划分时,尽量使用书数据耦合,少用控制耦合(转成数据耦合),限制公共耦合的范围,完全不用内容耦合

    内聚度

    内聚度是模块内部各成分(语句或者语句段)之间的联系,模块内部各成分联系越紧,其内聚度越大,模块独立性越强,系统越易理解和维护,良好的内聚度的模块应能较好的满足信息局部化的原则,功能完整单一模块的高内聚必然能导致模块的低耦合度,理想情况是,一个模块只使用局部数据变量,完成一个功能
    由弱到强的顺序,内聚读可分为7类:

    偶然内聚

    块中的各个任务(通过语句或指令来实现的)之间没有什么有意义的联系,他们之所以能构成一个模块完全是偶然的原因
    偶然内聚的模块有很多缺点:由于模块内没有实质性的联系,很可能在某种情况下一个调用模块需要对它修改而别的模块不需要,这时就很难处理,同时这种模块的含义也不易理解,甚至难以为他去一个何时的名字,偶然内聚的模块也难于测试,空间允许下,不应该使用偶然内聚

    逻辑内聚

    一个模块完成的任务在逻辑上属于相同或相似的一类(例如,用一个模块产生各种类型的输出)
    如: 模块A,B,C的功能相似但不相同,如果把他们合并成一个模块ABC,则这个模块就为逻辑内聚,因为他们是由于逻辑上相似而发生联系的,逻辑联系是一种较弱的联系,当X,Y,Z调用合成的ABC模块时,需要判别执行不同功能的哪一部分
    逻辑耦合存在的问题

    • 修改困难,调用模块中有一个要对其改动,还要考虑到其他调用模块
    • 模块内需要增加开关,判断是谁调用
    • 实际上每次调用只执行模块中的一部分,其他部分也被装入了内存,因而效率不高

    时间内聚

    时间内聚是指一个模块中包含的任务需要在同一时间内执行(如初始化,结束等所需操作)
    时间内聚和偶然内聚,逻辑内聚一样,都属于低内聚度类型

    过程内聚

    如果一个模块内的各个处理元素是相关的,而且必须按固定的次序执行,这种内聚就称为过程内聚,这种内聚往往表现为次序的流程

    通信内聚

    若一个模块中的各处理元素需引用共同的数据(同一数据项,数据区或文件),则称其元素间的联系为通信内聚,通信内聚的各部分是借助共同使用的数据联系在一起的,故有较好的可理解性,通信内聚和过程内聚属于中内聚度型模块

    顺序内聚

    若一个模块内的各处理元素关系密切,必须按规定的处理次序执行,则这样的模块为顺序内聚型,在顺序内聚模块内,后执行的语句或语句段往往依赖先执行的语句或语句段,以先执行的部分为条件,由于模块内各处理元素间存在着这种逻辑联系,所以顺序内聚模块的可理解性很强,属于高内聚度型模块

    功能耦合

    功能耦合是内聚度最高的一种模块类型,如果模块仅完成一个单一的功能,且该模块的所有部分是实现这一功能所必需的,没有多余的语句,则该模块为功能内聚型,功能内聚模块的结构紧凑,界面清晰,易于理解和维护,因而可靠性强,又由于其功能单一,故复用率高,所以他是模块划分时应追求的一种模块类型
    在模块设计时力争做到高内聚,并且能够辨别出低内聚的模块,加以修改使用提高内聚度并降低模块之间的耦合度

    • 设计功能单一的模块
    • 控制使用全局数据
    • 模块间尽量传递数据型变量
      构件(模块)设计的最终目的是将数据模型,架构模型,界面模型变为可以操作的软件,构件设计的详细程度可以根据项目的具体情况而定,在概要设计的时候,可以根据具体要求对各个模块进行详细设计,如果某项目开发过程中不存在详细设计过程,则可以将构件设计得尽可能详细,这样概要设计和详细设计合为一个过程
    展开全文
  • 内聚和耦合

    千次阅读 2019-02-13 14:30:48
    什么是内聚性 内聚是指一个模块的内部功能相互关联的紧密程度,执行某个特定的任务或相关任务组的模块是具有高内聚性的,而没有核心功能只是将大量功能凑到一起的模块具有低内聚性什么是耦合性 耦合是指模块 A 和...

    什么是内聚性

    内聚是指一个模块的内部功能相互关联的紧密程度,执行某个特定的任务或相关任务组的模块是具有高内聚性的,而没有核心功能只是将大量功能凑到一起的模块具有低内聚性。

    什么是耦合性

    耦合是指模块 A 和模块 B 功能上的相关程度。如果两个模块的功能在代码层面上高度重叠,即模块之间有方法的大量互相调用,那么这两个模块就是高耦合的。在模块 A 上的任何变动都会使得 B 变化。

    强耦合性不利于代码的可修改性,因为它增加了维护代码的成本,要提高代码的可修改性就应该做到代码的高内聚和低耦合。

    测量内聚性和耦合性

    举一个小例子来说明如何判断内聚性和耦合性。下面是模块 A 的代码:

    """ Module A(a.py) - Implement functions that operate on series of numbers """
    
    def squares(narray):
    	""" Return array of squares of numbers """
    	return pow_n(array, 2)
    
    def cubes(narray):
    	""" Return array of cubes of numbers """
    	return pow_n(array, 3)
    
    def pow_n(narray, n):
    	""" Return array of numbers raised to arbitrary power n each """
    	return [pow(x, n) for x in narray]
    
    def frequency(string, word):
    	""" Find the frequency of occurrences of word in string as percentage """
    	word_l = word.lower()
    	string_l = string.lower()
    
    	# words in string
    	words = string_l.split()
    	count = w.count(word_l)
    	
    	# return frequency as percentage
    	return 100.0 * count / len(words)
    

    然后是模块 B 的代码:

    """ Module B(b.py) - Implement functions provide some statistical methods """
    
    import a
    
    def rms(narray):
    	""" Return root mean square of array of numbers """
    	return pow(sum(a.squares(narray)), 0.5)
    
    def mean(array):
    	""" Return mean of an array of numbers """
    	return 1.0 * sum(array) / len(array)
    
    def variance(array):
    	""" Return variance of an array of numbers """
    	
    	# square of variation from mean
    	avg = mean(array)
    	array_d = [(x - avg) for x in array]
    	variance = sum(a.squares(array_d))
    	return variance
    
    def standard_deviation(array):
    	""" Return standard deviation of an array of numbers """
    	return pow(variance(array), 0.5)
    

    现在对模块 A 和 B 中的函数进行分析:

    模块核心功能数无关功能数功能依赖数
    B403 * 1 = 3
    A310

    1),模块 B 有 4 个函数,它们都是围绕核心功能的。该模块中没有与核心功能无关的功能,所有模块 B 有 100% 的内聚性。
    2),模块 A 有 4 个函数,其中 3 个是与核心功能相关的,但是最后一个 frequency 函数与核心功能无关,所以说 A 只有 75% 的内聚性。
    3),模块 B 中有 3 个函数依赖着模块 A 中的 square 函数的,这使得模块 B 与 模块 A 有强烈的耦合性,这里的模块 B 对于模块 A 在函数层面上的耦合性是 75%。
    4),模块 A 不依赖模块 B 中的任何函数,因此模块 A 是独立于模块 B 工作的,模块 A 对于模块 B 的耦合性是 0。

    如何改善

    想要提高模块 A 的内聚性可以很简单的将最后一个无关函数去掉,然后移植到其他模块中。
    现在分析从模块 B 到模块 A 的耦合性:
    1),B 中的 3 个函数只依赖 A 中的一个函数。
    2),A 中被依赖的函数为 square,其功能是接受一个数组并返回每个数组的平方。
    3),该函数的 API 很简单,因此在未来修改此函数 API 的可能性很小。
    4),系统中不存在两种耦合方式,依赖方向只有从 B 到 A。
    综上,尽管从 B 到 A 存在强耦合,但是这是一个 “好” 的耦合,而且丝毫不会影响系统的可修改性。

    另一个例子

    下面是模块 A 的代码:

    """ Mudule A(a.py) - Provides string processing functions """
    import b
    
    def ntimes(string, char):
    	""" Return number of times character 'char' occurs in string """
    	return string.count(char)
    
    def common_words(text1, text2):
    	""" Return common word across text1 and text2 """
    
    	# A text is a collection of strings split using newlines
    	strings1 = text1.split('\n')
    	strings2 = text2.split('\n')
    
    	common = []
    	for string1 in strings1:
    		for string2 in strings2:
    			common += b.common(string1, string2)
    	
    	# drop duplicates
    	return list(set(common))
    

    下面是模块 B 的代码:

    """ Module B(b.py) - Provides text processing functions to user """
    
    import a
    
    def common(string1, string2):
    	""" Return common words across string1 and string2 """
    
    	s1 = set(string1.lower().split())
    	s2 = set(string2.lower().split())
    	return s1.intersection(s2)
    
    def common_words(text1, text2):
    	""" Return common words across two input files """
    
    	lines1 = open(filename1).read()
    	lines2 = open(filename2).read()
    
    	return a.common_words(lines1, lines2)
    

    现在对模块 A 和 B 中的函数进行分析:

    模块核心功能数无关功能数功能依赖数
    B201 * 1 = 1
    A201 * 1 = 1

    1),模块 A 和模块 B 分别有两个函数,各个函数都是处理各自模块的核心功能,所以模块 A 和模块 B 都有 100% 的内聚性。
    2),模块 A 中有一个函数依赖于模块 B 中的一个函数,同时,模块 B 中有 一个函数也依赖于模块 A 中的一个函数。因此从模块 A 到模块 B 有强耦合性,从模块 B 到模块 A 也具有强耦合性。也就是说,耦合性是双向的。

    两个模块之间的双向耦合性就把每个模块的可修改性与对方紧密联系了起来,模块 A 中的任何修改将会迅速影响模块 B 的行为,反之亦然。因此这是一个 “坏” 的耦合。

    提高可修改性的策略

    提供显式接口

    一个模块应该为外部代码提供一组函数、类或方法作为接口。接口可以认为是模块的 API,实际上 API 就是从接口发展而来的。任何使用此模块 API 的外部代码都被称为此莫夸的客户。对于模块来说是内部的方法或函数,或者不是 API 的构成方法或函数,也应该明确加上私有标识,或被记录在案。

    减少双向依赖

    从上面第二个例子可以看出,如果耦合方向是单方面的,两个模块之间的耦合是可管理的,也就是说,它不会造成大的软件质量缺陷。然而,双向耦合使得两个模块之间紧密相连,进而使得模块难以被使用以及维护成本提高。
    某些语言(比如 python) 采用的是基于引用的垃圾回收机制,如果存在双向耦合,可能会导致变量与对象之间的隐式引用循环链,进而导致垃圾回收运行结果不理想。
    双向依赖可以用这样一种方式打破:第一个模块总是使用第二个模块之外的函数,第二个模块也可以这样做。也就是说,可以将各模块中共同使用的函数统一封装在一个模块中。
    上面举出的第二个例子可以简单的将模块 B 中的 common 函数移植到模块 A 中。

    抽象出公共服务

    使用抽象常用功能和方法的辅助模块可以减少两个模块之间的耦合,并增加他们的内聚性。在上面的第二个例子中,模块 A 相当于模块 B 的辅助模块。
    辅助模块可以认为是中间件或媒介,它抽象出其他模块的公共服务,使得被依赖的代码都被放在同一个地方,而不用在各模块中重复出现。另外,还可以把一个模块中与核心功能关联不大的函数移植到另一个辅助模块中,从而提高该模块的内聚性。

    使用继承技术

    当各个类中有相似的代码或函数时,可以使用类继承。使用继承方法使得各个类的通用代码通过继承共享。
    下面举一个例子,根据某个词的出现频率对文本文件进行排序:

    """ Module textrank - Rank text files in order of degree of a specific word frequency. 
    """
    
    import operator
    
    class TextRank(object):
    	""" Accept text files as inputs and rank them in terms of how much a word occurs 
    	in them """
    
    	def __init__(self, word, *filenames):
    		self.word = word.strip().lower()
    		self.filenames = filenames
    
    	def rank(self):
    		""" Rank the files. A tuple is returned with (filename, #occur) in decreasing
    		order of occurences """
    
    	occurs = []
    	for fpath in self.filenames:
    		with open(fpath, 'r') as f:
    			data = f.read()
    			words = map(lambda x: x.lower().strip(), data.split())
    			# filter empty words
    			count = words.count(self.word)
    			occurs.appen((fpath, count))
    	# return in sorted order
    	return sorted(occurs, key=operator.itemgetter(1), reverse=True)
    

    下面是另一个模块: urlrank。该模块对多个 URL 用同样的方法进行排序:

    """ Mudule urlrank - Rank URLs in order of degree of a specific word frequency """
    import operator
    import requests
    
    class URLRank(object):
    	""" Accept URLs as inputs and rank them in trems of how much a word occurs
    	in them """
    
    	def __init__(self, word, *urls):
    		self.word = word.strip().lower()
    		self.urls = urls
    
    	def rank(self):
    		""" Rank the URLs. A tuple is returned with (url, #occur) in decreasing
    		order of occurenecs """
    
    		occurs = []
    		for url in urls:
    			data = requests.get(url).text
    			words = map(lambda x: x.lower().strip(), data.split())
    			# filter empty words
    			count = words.count(self.word)
    			occurs.append((url, count))
    		
    		# return in sorted order
    		return sorted(occurs, key=operator.itemgetter(1), reverse=True)
    

    上面两个模块都是对多个输入的数据集进行排序,依据都是某个词在数据集中的出现频率,因此这两个模块中会有很多相似的代码,从而降低了可修改性,下面使用继承重构这两个模块。
    基类 RankBase:

    """ Mudule rankbase - Logic for ranking text using degree of word frequency """
    
    import operator
    
    class RankBase(object):
    	""" Accept text data as inputs and rank them in terms of how much a word occurs
    	in them """
    
    	def __init__(self, word):
    		self.word = word.lower().strip()
    
    	def rank(self, *texts):
    		""" Rank input data. A tuple is returnes with (idx, #occur) in decreasing
    		order of occurences ""'
    
    		words = map(lambda x: x.lower().strip(), text.split())
    		count = words.count(self.word)
    		occurs[idx] = count
    	
    		# return dictionary
    		return occurs
    	
    	def sort(self, occurs):
    		""" Return the ranking data in sorted order """
    		return sorted(occurs, key=operator.itemgetter(1), reverse=True)
    

    textrank 模块

    """ Module textrank - Rank text files in order of degree of specific word frequency """
    
    import operator
    from rankbase import RankBase
    
    class TextRank(RankBase):
    	""" Accept text files as inputs and rank them in terms of how much a word occurs
    	in them """
    
    	def __init__(self, word, *filenames):
    		super().__init__(word)
    		self.filenames = filenames
    
    	def rank(self):
    		""" Rank the files. A tuple is returned with (filename, #occur) in decreasing
    		order of occurences. """
    		texts = map(lambda x: open(x, 'r').read(), self.filenames)
    		occurs = super().rank(*texts)
    		occurs = [(self.filenames[x], y) for x, y in occurs.items()]
    		return self.sort(occurs)
    

    urlrank 模块:

    """ Mudule urlrank - Rank URLs in order of defree of a specific word frequency """
    
    import operator
    from rankbase import RankBase
    
    class URLRank(RankBase):
    	""" Accept URLs as inputs and rank them in terms of how much a word occurs in
    	them """
    
    	def __init__(self, word, *urls):
    		super().__init__(word)
    		self.urls = urls
    
    	def rank(self):
    		""" Rank the URLs. A tuple is returned with (url, #occur) in decreasing order
    		of occurences ""'
    
    		texts = map(lambda x: requests.get(x).text, self.urls)
    		occurs = super().rank(*texts)
    		occurs = [(self.urls[x], y) for x, y in occurs.items]
    		return self.sort(occurs)
    
    展开全文
  • 模块的7种内聚类型

    万次阅读 2019-03-31 15:17:46
    一个模块内部各元素之间的紧密程度越高,则其内聚性越高,模块独立性越好。模块内聚类型主要有以下几类: 偶然内聚或巧合内聚:指一个模块内的各处理元素之间没有任何联系。 逻辑内聚:指模块内执行若干个逻辑上...

    如果模块A的三个处理都对同一数据结构操作,则模块A的内聚类型是 通信内聚。


    模块间的耦合和模块的内聚是度量模块独立性的两个准则。内聚是模块功能强度的度量,即模块内部各个元素彼此结合的紧密程度。一个模块内部各元素之间的紧密程度越高,则其内聚性越高,模块独立性越好。模块内聚类型主要有以下几类:

    1. 偶然内聚或巧合内聚:指一个模块内的各处理元素之间没有任何联系。
    2. 逻辑内聚:指模块内执行若干个逻辑上相似的功能,通过参数确定该模块完成哪一个功能。
    3. 时间内聚:把需要同时执行的动作组合在一起形成的模块。
    4. 过程内聚:指一个模块完成多个任务,这些任务必须按指定的过程执行。
    5. 通信内聚:指模块内的所有处理元素都在同一数据结构上操作,或者各处理使用相同的输入数据或产生相同的输出数据。
    6. 顺序内聚:指一个模块中的各个处理元素都密切相关于同一各功能且必须顺序执行,前一个功能元素的输出就是下一个功能的输入。
    7. 功能内聚:指模块内的所有元素共同作用完成一个功能,缺一不可。
    展开全文
  • Java面试题大全(2020版)

    万次阅读 多人点赞 2019-11-26 11:59:06
    发现网上很多Java面试题都没有答案,所以花了很长时间搜集...1. JDK 和 JRE 有什么区别? JDK:Java Development Kit 的简称,java 开发工具包,提供了 java 的开发环境和运行环境。 JRE:Java Runtime Environ...
  • 内聚与耦合

    万次阅读 多人点赞 2019-05-16 14:52:21
    内聚低耦合 什么是内聚内聚有多少种类别 什么是耦合,耦合有多少种类别
  • 我们有两个定性的度量标准——耦合性和内聚性。 耦合性也称块间联系。指软件系统结构中各模块间相互联系紧密程度的一种度量。模块之间联系越紧密,其耦合性就越强,模块的独立性则越差,也就是说当我们改动一个...
  • ”高内聚 ,低耦合“到底是什么意思?

    万次阅读 多人点赞 2015-08-05 15:27:38
    总会听到大牛们说到“高内聚,低耦合”,不是...一个模块中各个元素之间的联系的紧密程度,如果各个元素(语句、程序段)之间的联系程度越高,则内聚性越高,即‘高内聚’ ! 如: 一个项目中有20个方法调用良好,
  • 摘要:做好高内聚低耦合,思路也很简单:定职责、做归类、划边界。 下面的这个场景你可能会觉得很熟悉(Z哥我又要出演了): Z哥:@All 兄弟姐妹们,这次我这边有个需求需要给「商品上架」增加一道审核,会影响到...
  • 什么是高耦合低内聚

    千次阅读 2018-01-18 19:33:52
    起因:模块独立性指每个模块只完成系统要求的独立子功能,并且与其他模块的联系最少且接口简单,两个定性的度量标准――耦合性和内聚性。 耦合性也称块间联系。指软件系统结构中各模块间相互联系紧密程度的一种度量...
  • 浅谈函数的内聚性

    千次阅读 2009-12-02 22:54:00
    在设计类的时候,抽象和封装已经很大程度上取代了内聚性。但是在子程序这一层次上,内聚性仍是常用的启发式方法。下面内容,来自《代码大全》对与子程序而言,内聚性是指子程序中各个操作之间的联系的紧密程度。我们...
  • 什么是内聚、低耦合?

    千次阅读 2014-12-16 10:45:55
    起因:模块独立性指每个模块只完成系统要求的独立子功能,并且与其他模块的联系最少且接口简单,两个定性的度量标准――耦合性和内聚性。 耦合性也称块间联系。指软件系统结构中各模块间相互联系紧密程度的一种度量...
  • MySQL 面试题

    万次阅读 多人点赞 2019-09-02 16:03:33
    什么是反模式? 艿艿:重点在于反模式的回答。实际开发中,不会严格遵守三范式。 胖友直接看 《服务端指南 数据存储篇 | MySQL(07) 范式与反模式》 。 MySQL 有哪些数据类型? MySQL 支持多种类型,...
  • 第五章 卷积神经网络

    千次阅读 多人点赞 2020-01-13 07:49:37
    第五章 卷积神经网络第五章 卷积神经网络卷积一维卷积二维卷积互相关卷积的变种卷积的数学性质交换导数卷积神经网络用卷积来代替全连接卷积层汇聚层(池化层)典型的卷积网络结构参数学习误差项的计算几种典型的卷积...
  • 低耦合,高内聚的详解(绝对全面)

    千次阅读 多人点赞 2018-03-17 17:01:48
    转载请注意出处:这几天又回顾了下java基础,突然看见松耦合这个字眼,很是疑惑,于是通过上网阅读多篇博客并结合翻阅的资料写下了这篇博客。...若一个程序之间各元素之间(程序段之间)联系紧密,则内聚性就高...
  • 面对对象原则:高内聚、低耦合

    千次阅读 2016-06-24 21:18:27
    这是软件工程中的概念,是判断设计好坏的标准,主要是面向OO的设计,主要是看类的内聚性是否高,偶合度是否低.每一个类完成特定的独立的功能,这个就是高内聚。耦合就是类之间的互相调用关系,如果耦合很强,互相...
  • 测试开发笔记

    万次阅读 多人点赞 2019-11-14 17:11:58
    什么是软件测试: 7 ★软件测试的目的、意义:(怎么做好软件测试) 7 3.软件生命周期: 7 第二章 测试过程 8 1.测试模型 8 H模型: 8 V模型 9 2.内部测试 10 3外部测试: 10 验收测试:(在系统测试之后) 11 回归...
  • SpringCloud面试题(二)

    万次阅读 2020-03-01 20:37:42
    SpringCloud面试题(二) 大家好,我是酷酷的韩金群~下面提供一些整理的springcloud面试题(二) ...为什么要使用微服务? 1.随着互联网的快速发展,各行各业都在用互联网。互联网已经离不开人们的形...
  • matlab人脸识别论文

    万次阅读 多人点赞 2019-10-11 17:41:51
    在某些可以控制拍摄条件的场合,如警察拍罪犯照片时将人脸限定在标尺,此时人脸的定位很简单。证件照背景简单,定位比较容易。在另一些情况下,人脸在图像 中的位置预先是未知的,比如在复杂背景下拍摄的照片,...
  • 推荐阅读: Android MVC设计模式详解 Android 框架MVVM详解 Android MVC设计模式详解 ...Java/Android 常见的设计模式总结,提高代码重用性和扩展下 ...耦合性(英语:Coupling,... 内聚性是一个和耦合性相...
  • 耦合 内聚加实例

    千次阅读 2018-02-09 14:10:00
    基本信息 耦合(或称"耦合度") 英文 : coupling 耦合也叫块间联系。指软件系统结构中各模块间...形象的说,就是要将代码写的和电脑一样,主类就是电脑的主机箱,当程序需要实现什么功能的时候只需要在其他...
  • 内聚低耦合思想

    千次阅读 2017-12-01 11:54:06
    指每个模块只完成系统要求的独立子功能,并且与其他模块的联系最少且接口简单,两个定性的度量标准――耦合性和内聚性。 耦合性 耦合性也称块间联系。指软件系统结构中各模块间相互联系紧密程度的一种度量。模块...
  • Spring面试题

    千次阅读 多人点赞 2018-06-26 14:58:42
    对组件的调用者而言,组件内部的依赖关系完全透明,更符合高内聚的原则。 三、Spring Framework 中的模块 Spring 核心容器 – 该层基本上是 Spring Framework 的核心。它包含以下模块: Spring Core ...
  • SDN

    千次阅读 多人点赞 2017-06-29 11:35:37
    SDN的本质定义就是软件定义网络,也就是说希望应用软件可以参与对网络的控制管理,满足上层业务需求,通过自动化业务部署简化网络运维。 1 SDN标准:ONF 网站:... ... ...SDN的核心:可编程 SDN
  • 什么是数据的高内聚、低耦合

    千次阅读 2015-11-14 15:35:01
     起因:模块独立性指每个模块只完成系统要求的独立子功能,并且与其他模块的联系最少且接口简单,两个定性的度量标准――耦合性和内聚性。  耦合性也称块间联系。指软件系统结构中各模块间相互联系紧密程度的一...
  • 史上最全面Java面试汇总(面试题+答案)

    万次阅读 多人点赞 2018-07-06 14:09:25
    什么是泛型、为什么要使用以及泛型擦除 泛型,即“参数化类型”。 创建集合时就指定集合元素的类型,该集合只能保存其指定类型的元素,避免使用强制类型转换。 Java编译器生成的字节码是不包涵泛型信息的,泛型类型...
  • 关于高内聚低耦合的理解

    千次阅读 2017-11-10 16:30:00
    对高内聚低耦合的理解

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 60,053
精华内容 24,021
关键字:

其中内聚性是什么