-
Notifications
You must be signed in to change notification settings - Fork 2k
Expand file tree
/
Copy pathTAfferentCoupling.qhelp
More file actions
80 lines (66 loc) · 2.67 KB
/
TAfferentCoupling.qhelp
File metadata and controls
80 lines (66 loc) · 2.67 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
<!DOCTYPE qhelp PUBLIC
"-//Semmle//qhelp//EN"
"qhelp.dtd">
<qhelp>
<overview>
<p>
This metric measures the number of incoming dependencies for each reference
type, i.e. the number of other types that depend on it.
</p>
<p>
Types that are depended upon by many other types typically require a lot of
effort to change, because changing them will force their dependents to change
as well. This is not necessarily a bad thing -- indeed, most systems will have
some such types (one example might be a string class). However, types with a high number
of incoming dependencies
and a high number of outgoing dependencies are hard to maintain. A type with both high afferent
coupling <em>and</em> high efferent coupling is referred to as a hub type.
Such types can be problematic, because on the one hand they are hard to
change (high afferent coupling), yet on the other they have many reasons to
change (high efferent coupling). This contradiction yields code that is very
hard to maintain or test.
</p>
<p>
Conversely, some types may only be depended on by very few other types. Again,
this is not necessarily a problem -- we would expect, for example, that the
top-level types of a system would meet this criterion. When lower-level
types have very few incoming dependencies, however, it can be an indication
that a type is not pulling its weight. In extreme cases, types may even
have an afferent coupling of <code>0</code>, indicating that they are dead
code.
</p>
</overview>
<recommendation>
<p>
It is unwise to refactor a type based purely on its high or low number of
incoming dependencies -- a type's afferent coupling value only makes sense
in the context of its role in the system as a whole. However, when combined
with other metrics such as efferent coupling, it is possible to make some
general recommendations:
</p>
<ul>
<li>
Types with high numbers of incoming <em>and</em> outgoing dependencies
are hub types that are prime candidates for refactoring (although this
will not always be easy). The general strategy is to split the type into
smaller types that each have fewer responsibilities, and refactor the code
that previously used the hub type accordingly.
</li>
<li>
Types that have very few incoming dependencies and are not at the top level
of a system may not be pulling their weight and should be refactored, e.g.
using the 'Collapse Hierarchy' or 'Inline Class' techniques in [Fowler]
(see the section entitled 'Lazy Class' on p.68).
</li>
<li>
Types that have an afferent coupling of <code>0</code> may be dead code --
in this situation, they can often be deleted.
</li>
</ul>
</recommendation>
<references>
<li>
M. Fowler. <em>Refactoring</em>. Addison-Wesley, 1999.
</li>
</references>
</qhelp>