Dieser Blogpost ist auch auf Deutsch verfügbar

TL;DR

  • Cohesion is ambiguous, because “relatedness” can be understood differently depending on the architectural goal.
  • Functional cohesion measures whether elements serve the same purpose within the system context.
  • Cohesion concerns a single component; misplaced logic increases coupling, not cohesion.
  • One heuristic for poor modularization: component descriptions that contain “and”, a time reference, or a vague object.

For a client workshop, I wanted to discuss the tactics “reduce coupling” and “increase cohesion” alongside other architectural tactics. For that, I needed definitions of these terms that were as simple and precise as possible, short enough to fit on an index card.

In the case of coupling, this was done relatively quickly: there are a number of definitions, and they all ultimately come down to the degree to which changes to one system component also require changes to other components [1]. In the case of cohesion, it was considerably harder. In my mind, cohesion somehow described how much the things within a component have to do with one another.

In the literature, too, the descriptions are often not much more precise: Constantine and Yourdon [1], for example, describe cohesion as “intramodular functional relatedness”. Bass, Clements, and Kazman [2] describe cohesion as the probability that a change scenario affecting one responsibility of a component will also affect other responsibilities of the same component. That is a bit more concrete, but somewhat cumbersome, and it leaves open what exactly is meant by responsibilities. I adopted this definition for my index card anyway. Then, during the workshop, I was met with many puzzled faces.

Discussions with colleagues also revealed wide divergence in opinions about what cohesion actually means. In this article, I therefore want to try to understand more precisely what cohesion is. This will show that cohesion is not an absolute measure, but depends heavily on the context and the quality goals you pursue with the modularization of the system.

Why Do We Split Software into Components?

Cohesion is a property of a component within a larger system. The concept is meant to help find a division of a system into components that is useful for the specific use case.

The idea of splitting software into components was already used in Dijkstra’s T.H.E. system [3] to reduce the complexity of the overall system. David Parnas [4] also saw modularization as a way to improve a system’s modifiability and understandability.

At its core, the motivation for modularization is that the overall system is too large to grasp as a whole, so it is worthwhile to only have to consider smaller parts of the system at a time.

What Is Cohesion?

The term “cohesion” was introduced (together with coupling) by Stevens, Myers, and Constantine [5]. The primary motivation was to find modularizations of a system that made it easy to carry out changes locally, without affecting other parts of the system. A second motivation here, too, was to increase the comprehensibility of the system. Being able to make changes as locally as possible is ultimately the definition of the term “coupling”.

Cohesion (from the Latin cohaerere, to hang together) was introduced by Stevens, Myers, and Constantine based on a simple heuristic: if you group elements of a system that are strongly related to one another into the same component, you reduce the dependencies between different components, because the strong dependencies have been moved into the components. By analogy with other disciplines such as sociology, Stevens, Myers, and Constantine chose the term “cohesion” to describe this high degree of relatedness within a component.

Some time ago, there was a discussion among colleagues at INNOQ about whether java.lang.Math (the Java standard library implementations of important mathematical functions) has high or low cohesion.

The arguments for both sides were essentially:

  • java.lang.Math has high cohesion, because all its elements are fundamental mathematical functions.
  • java.lang.Math has low cohesion, because its elements are implemented independently of one another (this isn’t entirely true, but for the sake of this discussion let’s assume it were).

So what does “relatedness” mean? That things depend on one another (a kind of “internal coupling”), or that the underlying domain concepts are close?

Stevens, Myers, and Constantine themselves already provide an answer to this question by describing different levels of cohesion, among them the highest levels of sequential cohesion (which would include the outputs of one element serving as inputs to the next) and functional cohesion (the elements serve one domain purpose). In this sense, then, whether java.lang.Math has high cohesion depends essentially on whether you regard “providing mathematical functions” as a domain purpose or not.

This shows that the notion of relatedness can depend heavily on the context in which, and the goal with which, the modularization of the system is considered. It also explains why there is so much disagreement when you ask what cohesion actually means, and why definitions of cohesion often remain somewhat vague.

What Do We Need Cohesion For?

Let’s take a step back and look again at the motivation behind the term “cohesion”. High cohesion is not an end in itself. It is a means (an architectural tactic) for achieving higher-level quality goals. Depending on what those goals are, a different notion of “relatedness” can be useful.

For java.lang.Math, there are two goals that could be relevant:

  • Java developers should be able to use the standard library well. For that, it is important that functionality can be found easily. As a Java developer, when I need a mathematical function, the first place to look at would be java.lang.Math. (Thanks to IDE support, this goal is now less relevant than it probably was at the beginning of the Java standard library’s development.)
  • New mathematical functions and performance optimizations of the existing ones should be supported by the component structure. Both goals suggest that it is a good idea to group all elements that fulfill the purpose “provide mathematical functions” into one component.

On the other hand, the question of whether the elements of a component call one another is highly relevant when the goal is, say, better understandability or modifiability of the system. Here, too, it becomes clear that the concrete goals have a major influence on how cohesion is assessed.

Purpose and Descriptions

There is one form of cohesion that is much easier to pin down, and that Stevens, Myers, and Constantine describe as the highest degree of cohesion: functional cohesion. It is the degree to which the elements of a component serve the same purpose within the system context.

The purpose of a component answers the question: what does the component exist for? Ideally, you can find descriptions for each component that delimit this purpose. In their article, Stevens, Myers, and Constantine describe criteria for how, based on these descriptions, you can tell that a component does not have high functional cohesion. Let’s take a closer look at these criteria.

Components with Several Purposes

Multiple sentences, words like “and”, commas, or several verbs indicate that the component serves several purposes and could therefore be split. In that case, you should probably divide the component into several parts. This is something fundamentally different from looking at the modularization at a different level of abstraction:

For example, a payroll system might consist of several components: a payroll calculation component that computes the net pay to be paid out for each employee, a salary payout component that triggers the payout, and a tax reporting component that aggregates the withheld wage tax amounts and transmits them to the tax authority. The payroll calculation component, in turn, consists of a component for gross pay calculation, for example from base salary and bonus payments, and a component for determining tax and social security deductions.

The payroll calculation component fulfills a single purpose within the overall system (“determine net pay”) that goes beyond the purposes of gross pay calculation and of determining the deductions. Conversely, there would be no overarching purpose if the salary payout and tax reporting components were merged. Here the purpose would then be something like “transfer net wages to employees and transmit wage tax amounts to the tax office”. This purpose description would be a clear sign that the components should be kept separate within the overall system.

This principle is also crucial for the heuristic that high cohesion implies low coupling: in the example, both the payroll calculation component as a whole and its two subcomponents have high cohesion, but at the level of the subcomponents there is coupling between them. The heuristic applies only at the level at which cohesion is considered.

Temporal Dependencies

If the descriptions contain words that refer to time, such as “first”, “then”, or “after”, that indicates that the component’s elements are merely executed at the same time and do not serve a common domain purpose. The same goes for words like “initialization” or “cleanup”.

The classic example is initialization components: a component that, “after the system has started, first establishes the database connection, loads the configuration, and then starts the notification service”, groups things together because they all happen at startup, not because they belong together in domain terms. Those tasks would be better placed in the components responsible for the relevant domain logic. This has the positive side effect that coordination between the components (such as temporal dependencies) is modeled explicitly and does not lie implicitly in the order of the calls.

Missing Specific Object

The third criterion concerns the specificity of the description: if the object in the sentence is described in very general terms, for instance, with words like “all”, “any kind of”, or “every”, that indicates the component groups tasks not by domain criteria, but by technical ones.

Stevens, Myers, and Constantine give the example “Edit All Data” as opposed to “Edit Source Statement”: the first groups all data validations together because they are technically similar; the second describes a single, clearly delimited function.

Good Descriptions

Finding good descriptions, however, extends beyond the mentioned criteria: good descriptions for components should ensure that, within the system context, it’s clear which component a given piece of functionality belongs to. They should be short and understandable, ideally without requiring deep technical knowledge. This not only prevents low cohesion within individual components but also high coupling caused by related functionality spread across several components.

Good descriptions reduce cognitive load, because developers can usually restrict themselves to a limited part of the system. They improve the understandability of the code and the extensibility of the system, since it becomes clearer which part of the system should contain which functionality. This is especially relevant at high levels of abstraction, particularly in complex systems, when, for example, different teams are responsible for the different components. Finding good descriptions is hard and time-consuming, but it pays off in the long run.

Coupling and Cohesion

Delimitation

In contrast to coupling, cohesion always refers to only a single component within the system context. Let’s take as an example a content management system with an article component that manages articles, and a URL router that maps URLs to content. As a new feature, slugs are to be generated for articles from the title and metadata (“My Article” becomes “my-article-2026–06–24”). Since the slugs appear in URLs, the development team decides to implement the logic in the URL router.

From a domain perspective, however, a slug is a property of the article. It is derived from the title and metadata and makes no sense outside the article context. The fact that the logic sits in the URL router has not made the cohesion of the article component any worse, though: the component itself has not changed.

What does change is the coupling: the URL router now has to access the title and metadata of the articles directly. Had the slug generation been implemented in the article component, the URL router would instead simply call article.slug(), and the dependency would be limited to a single method.

So: cohesion only describes how much things within a component are related. Functionality that belongs to a component in domain terms but is implemented elsewhere does not worsen the cohesion of that component, but it typically increases the coupling between the components involved.

Does High Cohesion Imply Low Coupling?

The original motivation behind introducing cohesion was that it is easier to increase cohesion than to reduce coupling, since you only have to look at one component at a time, whereas coupling always refers to the interaction between components. The heuristic can be justified by the fact that the interfaces of a highly cohesive component can be kept leaner and simpler when the purpose of the component can be described and delimited more clearly.

Conclusion

Based on this analysis, we can define cohesion as follows: a component has high cohesion when all of its elements serve the same, clearly describable purpose within the system context.

The key point is the phrase “within the system context”: cohesion is not an absolute measure, but always relative to the modularization goals. Understandability, modifiability, and reusability may prioritize different forms of “relatedness”. The definition above aligns with the special case of functional cohesion described by Stevens, Myers, and Constantine, the strongest form of cohesion.

The most important practical consequence: good component descriptions aren’t just a nice-to-have—they’re the key tool for high cohesion, as Michael Plöd [6] also writes. If you can describe a component clearly in one sentence and without an “and”, you very likely have a cohesive component.

  1. Yourdon, E., & Constantine, L. L. (1979). “Structured Design: Fundamentals of a Discipline of Computer Program and Systems Design”. Pearson Education.  ↩︎

  2. Bass, L., Clements, P., & Kazman, R. (2012). “Software Architecture in Practice”. Addison-Wesley Professional.  ↩︎

  3. Dijkstra, E. W. (1968). “The Structure of the ‘THE’-Multiprogramming System”. Communications of the ACM, 11(5), 341–346. https://doi.org/10.1145/363095.363143  ↩︎

  4. Parnas, D. L. (1972). “On the criteria to be used in decomposing systems into modules”. Communications of the ACM, 15(12), 1053–1058. https://doi.org/10.1145/361598.361623  ↩︎

  5. Stevens, W. P., Myers, G. J., & Constantine, L. L. (1974). “Structured Design”. IBM Systems Journal, 13(2), 115–139. https://doi.org/10.1147/sj.132.0115  ↩︎

  6. Plöd, M. (2025). “Bounded Contexts Are All About Cohesion”. https://www.michael-ploed.com/blog/bounded-contexts-are-all-about-cohesion. Retrieved on 2026–06–25.  ↩︎