Notaciones de diagrama de clase UML: diferencias entre asociación, agregación y composición

39

Estoy confundido acerca de algunas de las notaciones de los diagramas de clases UML.

ingrese la descripción de la imagen aquí

Estoy bastante seguro de saber lo que significa Asociación . Cualquier relación entre instancias de dos clases, donde una instancia de una clase necesita saber sobre una instancia de la segunda clase para realizar su trabajo, es una relación de asociación. Una asociación a menudo significa que la clase A tiene una referencia (campo) a una instancia de la clase B.

Sin embargo, tengo problemas para entender lo que significan las flechas de Agregación y Composición . Parte de mi confusión fue causada por encontrar diferentes definiciones de estas anotaciones.

Dos definiciones de la notación de agregación :

Definición 1: una notación de agregación entre dos clases es adecuada siempre que una instancia de la clase A contenga una colección de instancias de la clase B (por ejemplo, una lista, matriz, lo que sea).

Definición 2: Un enlace de agregación entre dos clases es adecuado si una instancia de la clase A contiene una referencia a una instancia de la clase B, y la instancia B depende del ciclo de vida de la instancia A. Significado: cuando la instancia de la clase A se elimina, también lo hará la instancia de la clase B. La instancia de la clase B está completamente contenida por la instancia de la clase A, en oposición a la instancia de la clase A, simplemente teniendo una referencia a la instancia de clase B (que es la asociación regular).

Con respecto a lo que significa la notación de composición y cómo difiere de la notación de agregación, no estoy seguro.

Por favor aclare las definiciones y ayúdeme a entender. Ejemplos concretos serían bienvenidos.

Aviv Cohn
fuente
La definición 2 suena más como la definición de composición que de agregación. La definición 1 suena bastante bien.
jbx

Respuestas:

32

Los tres enlaces Asociación, Agregación y Composición forman una especie de escala sobre cuán estrechamente se relacionan dos clases entre sí.

En un extremo de la escala, hay una Asociación, donde los objetos de las dos clases pueden conocerse entre sí, pero no afectan la vida de los demás. Los objetos pueden existir independientemente y qué objeto de clase A sabe qué objetos de clase B pueden variar con el tiempo.

En el otro extremo de la escala, hay Composición. La composición representa una relación parte - todo tal que la clase B es una parte integral de la clase A. Esta relación se usa típicamente si los objetos de la clase A no pueden existir lógicamente sin tener un objeto de clase B.

La relación de agregación se encuentra en algún punto entre esos dos extremos, pero nadie parece estar de acuerdo exactamente dónde, por lo que tampoco existe una definición universalmente aceptada de lo que significa una agregación. En ese sentido, ambas definiciones que encontró son correctas y si pregunta a 10 personas, corre el riesgo de obtener 11 definiciones diferentes.

Bart van Ingen Schenau
fuente
1
Gracias por tu respuesta. Así es como entiendo las cosas, por favor diga si esta es una definición razonable. 1- La asociación es cuando un objeto A necesita saber acerca de un objeto B para realizar su funcionalidad. 2- Tanto la agregación como la composición definen una relación de 'propiedad': una instancia de clase A conceptualmente posee una instancia de clase B. Pero la vida útil de la instancia B es independiente de la vida útil de la instancia A. Por ejemplo, un departamento con empleados. El departamento 'posee' instance instancia de empleado, pero seguirá viviendo sin el departamento. La composición es como la agregación, pero
Aviv Cohn
1
la vida útil de la instancia B depende de la vida útil de la instancia A. Una relación de 'propiedad' más fuerte. Por ejemplo: un auto y una rueda. El auto 'contiene completamente' la rueda. La instancia de Wheel no continuará viviendo sin la instancia de Car que la contenga. ¿Es esta una diferenciación razonable?
Aviv Cohn
@Prog: Sí, esa es una definición razonable. Solo recuerde que otros pueden no compartir esa definición y que es posible que deba explicarles su uso de la agregación.
Bart van Ingen Schenau
¿Cuál diría que es la definición más común para la notación de agregación? La definición que estoy usando? La definición 'tiene una colección de'? ¿Algo más?
Aviv Cohn
La referencia al estándar OMG a continuación es instructiva. La asociación y la composición son bastante sencillas. La agregación es la tambaleante. En la práctica, encuentro que la prueba 'parte de' funciona bien ('propiedad' es una forma subóptima de pensarlo). Una persona puede ser parte de un club, por lo tanto, un club agrega personas (no las posee). Cuando se destruye el club, la gente sigue existiendo.
Huliax
10

La composición es cuando un object Acontiene object By el object Atambién es responsable de crear el object B.

Relación de composición

Tenemos una clase A que será utilizada por la clase B.

final class A
{
}

Hay múltiples opciones sobre cómo puede verse la composición.

Composición de inicialización directa:

final class B
{
    private $a = new A();
}

Composición de inicialización del constructor

final class B
{
    private $a;

    public function __construct()
    {
        $this->a = new A();
    }
}

Composición de inicialización perezosa

final class B
{
    private $a = null;

    public function useA()
    {
        if ($this->a === null) {
            $this->a = new A();
        }

        /* Use $this->a */
    }
}

Usted ve que esto crea una estrecha relación entre las clases Ay B. La clase Bsimplemente no puede existir sin ella A. Esta es una gran violación del principio de inyección de dependencia , que dice:

Una dependencia es un objeto que se puede usar (un servicio). Una inyección es el paso de una dependencia a un objeto dependiente (un cliente) que lo usaría. El servicio forma parte del estado del cliente. Pasar el servicio al cliente, en lugar de permitir que un cliente construya o encuentre el servicio, es el requisito fundamental del patrón.

La composición a veces tiene sentido, como llamar new DateTimea php o new std::vector<int>en C ++. Pero la mayoría de las veces, es una advertencia, que el diseño de su código es incorrecto.

En un caso, donde class Asería un objeto especial utilizado para el almacenamiento en caché, class Bsiempre se almacenaría en caché utilizando la implementación de class A, y no tendría control para cambiarlo dinámicamente, lo cual es malo.

Además, si usó la composición de inicialización diferida , lo que significa que tendría un funcionamiento object B, llamado useA()método y la creación de object Afallaría, su de object Brepente es inútil.


La agregación, por otro lado, es una forma de relación, que sigue el principio DI . object Bnecesita usar object A, entonces debería pasar la instancia de object Ato ya creada object B, y si la creación de object Afalla, no se pasaría nada en primer lugar.

En resumen, la agregación es una representación UML para el principio de inyección de dependencia , ya sea inyección de constructor, inyección de setter o inyección de propiedad pública.

Estas son todas las agregaciones

La inyección de constructor más ajustada ( object Bno puede existir sin object A).

final class B
{
    private $a;

    public function __construct(A $a)
    {
        $this->a = $a;
    }
}

Más flojo (puede usarlo o no object Adentro object B, pero si lo hace, probablemente debería configurarlo primero).

Vía setter:

final class B
{
    private $a;

    public function setA(A $a)
    {
        $this->a = $a;
    }
}

Vía propiedad pública:

final class B
{
    public $a;
}

Realmente no hay una buena manera de justificar el uso de la agregación sobre la composición, si todo lo que está utilizando son implementaciones concretas de clases, pero una vez que comience a inyectar interfaces o en el caso de clases abstractas de C ++, de repente la agregación será la única forma de Cumplir su contrato.

Andy
fuente
1
¡Ver ejemplos de código realmente ayuda! Las explicaciones en inglés sin código parecen muy vagas y subjetivas.
Niko Bellic
1

Además un extracto del estándar UML actual:

11.5.4 Asociaciones - Semántica - Notación

[...] Una asociación binaria puede tener un extremo con aggregation = AggregationKind :: shared o aggregation = AggregationKind :: composite. Cuando un extremo tiene agregación = AggregationKind :: shared, se agrega un diamante hueco como adorno terminal al final de la línea de Asociación opuesta al extremo marcado con agregación = AggregationKind :: shared. El diamante será notablemente más pequeño que la notación de diamante para las asociaciones. Una asociación con agregación = AggregationKind :: composite también tiene un diamante en el extremo correspondiente, pero difiere en tener el diamante relleno . […]

9.5.4 Clasificación - Propiedades - Notación

[…] A veces, una Propiedad se usa para modelar circunstancias en las que una instancia se usa para agrupar un conjunto de instancias; Esto se llama agregación. Para representar tales circunstancias, una propiedad tiene una propiedad de agregación, de tipo AggregationKind; la instancia que representa a todo el grupo está clasificada por el propietario de la Propiedad, y las instancias que representan a los individuos agrupados se clasifican por el tipo de Propiedad. AggregationKind es una enumeración con los siguientes valores literales:

  • none : indica que la propiedad no tiene semántica de agregación.
  • Compartido : indica que la propiedad ha compartido semántica de agregación. La semántica precisa de la agregación compartida varía según el área de aplicación y el modelador.
  • Compuesto : indica que la propiedad se agrega de manera compuesta, es decir, el objeto compuesto tiene la responsabilidad de la existencia y el almacenamiento de los objetos compuestos (consulte la definición de partes en 11.2.3). La agregación compuesta es una forma fuerte de agregación que requiere que se incluya un objeto parcial en, como máximo, un objeto compuesto a la vez. Si se elimina un objeto compuesto, todas sus instancias parciales que son objetos se eliminan con él.

[...]

ManuelSchneid3r
fuente
0

Ya publiqué una respuesta en Stackoverflow .

Básicamente, una agregación es más fuerte que una asociación simple, pero los objetos agregados pueden "vivir" uno sin el otro como con una asociación simple.

Una composición es incluso más fuerte que una agregación porque la clase agregada no puede ser agregada por otras clases. Su "vida" depende del contenedor.

C.Champagne
fuente