В чем разница между объединением, агрегацией и составом?


389

В чем разница между объединением, агрегацией и составом? Пожалуйста, объясните с точки зрения реализации.


2
Для новичка это может показаться немного сложным , но прогуляйтесь по спецификации UML 2 Superstructure: omg.org/docs/formal/09-02-02.pdf Раздел 7.3.3 для ассоциации
chickeninabiscuit

6
Я также должен добавить, что в UML 2 нет такого элемента, как Aggregation или Composition (хотя это было в UML 1.4). В UML 2 агрегация / составление реализованы как элементы Association со свойством AggregationKind, установленным в Shared или Composite.
куриное печенье

Уже много ответов на SO: stackoverflow.com/search?q=aggregation+and+composition
лотерея

2
полезная статья здесь codeproject.com/Articles/22769/…
GibboK

6
Я знаю, что на это уже отвечали много раз, но я чувствую, что лучшее объяснение, которое я когда-либо читал по этому вопросу, было следующим: holub.com/goodies/uml/#composition
WLin

Ответы:


385

Для двух объектов Fooи Barотношений могут быть определены

Ассоциация - у меня есть отношения с объектом. FooиспользованияBar

public class Foo { 
    void Baz(Bar bar) {
    } 
};

Композиция - я владею объектом и отвечаю за его жизнь. Когда Fooумирает, так жеBar

public class Foo {
    private Bar bar = new Bar(); 
}

Агрегация - у меня есть объект, который я позаимствовал у кого-то другого. Когда Fooумрет, Barможет жить дальше.

public class Foo { 
    private Bar bar; 
    Foo(Bar bar) { 
       this.bar = bar; 
    }
}

3
Кажется C # / Java-код. В этом случае и код ассоциации, и код агрегации совпадают. В обоих случаях просто указывается «bar», и Barобъект может жить.
Ajay

@ Джефф Фостер: У меня есть некоторые сомнения. Если я создаю экземпляр объекта bar в Baz (Bar bar) {bar = new Bar (); } в первом случае. Это все еще будет ассоциация или она станет композицией сейчас?
Сакет

21
@Ajay: Агрегация сохраняет ссылку на объекты, что не относится к ассоциации. Отсюда и разница реализации.
ABCD

17
Ассоциация немного сильнее, чем просто использование в качестве параметра метода. Я полагаю, что ваш фрагмент кода ассоциации больше соответствует отношению зависимости . Возможно, вы захотите проверить статью, связанную с Мартином Фаулером
Ахмад Абдельхани

5
@AhmadAbdelghany - это правильно. Первый пример - это зависимость. Третий работает для объединения и агрегирования.
Андре Валенти

123

Я знаю, что этот вопрос помечен как C #, но концепции являются довольно общими вопросами, такими как перенаправление здесь. Так что я собираюсь изложить свою точку зрения здесь (немного предвзято с точки зрения Java, где мне удобнее).

Когда мы думаем об объектно-ориентированной природе, мы всегда думаем об объектах, классе (чертежах объектов) и отношениях между ними. Объекты связаны и взаимодействуют друг с другом с помощью методов. Другими словами, объект одного класса может использовать службы / методы, предоставляемые объектом другого класса. Этот вид отношений называется ассоциацией. ,

Агрегация и композиция являются подмножествами ассоциации, то есть они являются конкретными случаями ассоциации.

введите описание изображения здесь

  • И в агрегации, и в композиции объект одного класса «владеет» объектом другого класса .
  • Но есть небольшая разница. В Composition объект класса, который принадлежит объекту своего класса-владельца, не может жить сам по себе (также называемый «смертью отношений»). Он всегда будет жить как часть своего объекта-владельца, где, как и в Aggregation, зависимый объект является автономным и может существовать, даже если объект-владелец класса мертв.
  • Таким образом, по составу, если принадлежащий объект является сборщиком мусора, принадлежащий объект также будет, что не относится к агрегации.

Смущенный?

Пример композиции : рассмотрим пример автомобиля и двигателя, который очень специфичен для этого автомобиля (то есть его нельзя использовать ни в каком другом автомобиле). Этот тип отношений между классом Car и SpecificEngine называется Composition. Объект класса Car не может существовать без объекта класса SpecificEngine, а объект класса SpecificEngine не имеет значения без класса Car. Проще говоря, класс Car является единственным владельцем класса SpecificEngine.

Пример агрегации : теперь рассмотрим класс Car и класс Wheel . Автомобиль нуждается в объекте Колесо, чтобы функционировать. То есть объект Car владеет объектом Wheel, но мы не можем сказать, что объект Wheel не имеет значения без объекта Car. Он может очень хорошо использоваться в Велосипеде, Грузовике или другом Объекте Автомобилей.

Подводя итог -

Подводя итог, можно сказать, что ассоциация - это очень общий термин, используемый для обозначения того, когда класс использует функции, предоставляемые другим классом. Мы говорим, что это композиция, если один объект родительского класса владеет другим объектом дочернего класса, и этот объект дочернего класса не может существенным образом существовать без объекта родительского класса. Если это возможно, то это называется Агрегация.

Подробнее здесь. Я являюсь автором http://opensourceforgeeks.blogspot.in и добавил ссылку выше на соответствующий пост для большего контекста.


8
Я собирался спросить, почему вы решили ответить на уже отвеченный вопрос, который был задан более 5 лет назад, но затем я прочитал вашу запись в блоге, и она была намного более информативной, чем некоторые ответы здесь. Upvoted!
Донбхупи

2
Я согласен с @Donbhupi, ваш ответ более информативен и
точен,

1
Это действительно забавно, когда разработчики C # и Java утверждают, что используют композицию, когда она существует только в примитивных типах с этими языками. Если вы хотите по-настоящему понять композицию, вы должны использовать C ++, где объекты могут ДЕЙСТВИТЕЛЬНО быть частью других объектов .. Не просто плавать в памяти кучи и удерживать указатели друг на друга и утверждать, что есть композиция ..
Все

@ Каждый пришел к такому же выводу, как и ты, но я не уверен в этом. Например, скажем, у меня есть один класс, который семантически принадлежит одному конкретному классу, однако принадлежащий объект является сборщиком мусора после того, как его владелец уже удален сборщиком мусора, это считается составом?
Пауло Андре Хааке

Можем ли мы иметь композицию в коде ac #, используя управляемую память?
Пауло Андре Хааке

86

Ассоциация является обобщенной концепцией отношений. Включает в себя как состав, так и агрегацию.

Композиция ( смесь ) - это способ объединить простые объекты или типы данных в одну единицу . Композиции являются важным строительным блоком многих базовых структур данных.

Агрегация ( сбор ) отличается от обычного состава тем, что не предполагает владения. В композиции, когда владелец объекта уничтожается, также и содержащиеся объекты. В совокупности это не обязательно верно.

Оба обозначают отношения между объектами и отличаются только их силой.

Trick помнить разницу: есть A - A ggregation и O WN - C O mpositoin

введите описание изображения здесь

Теперь давайте посмотрим на следующее изображение

связи

введите описание изображения здесь

Аналогия:

Композиция : Следующая картинка представляет собой композицию изображения, т.е. использует отдельные изображения, составляющие одно изображение.
введите описание изображения здесь

Агрегация : коллекция изображений в одном месте

введите описание изображения здесь

Например, университет имеет различные факультеты, и на каждом факультете есть несколько профессоров. Если университет закроется, кафедры больше не будут существовать, но профессора на этих кафедрах продолжат существовать. Следовательно, университет можно рассматривать как состав кафедр, тогда как кафедры имеют совокупность профессоров. Кроме того, профессор может работать более чем на одном факультете, но факультет не может быть частью более чем одного университета.


14
Прочитав так много на эту тему, этот ответ является наиболее интуитивно понятным. Надо ставить на википедию.
Jankapunkt

1
Красиво сформулированный.
Сид

Что касается агрегации, вы говорите: «Дочерние объекты принадлежат одному родителю». Это не правильно. Допустимо, чтобы UML имел общую агрегацию, т. Е. Ребенок принадлежит нескольким родителям. Вы признаете это в своем примере об отделе как о совокупности профессоров, потому что вы говорите, что профессор может работать в более чем одном отделе.
www.admiraalit.nl

@ www.admiraalit.nl Общая агрегация AFAIK не означает, что «ребенок принадлежит к нескольким родителям», а наоборот, несколько детей принадлежат к одним и тем же родителям. И это несоставная агрегация, потому что даже если родители умрут, дети могут выжить дольше.
aderchox

65

Зависимость (ссылки)
Это означает, что между двумя объектами нет концептуальной связи. например, объект EnrollmentService ссылается на объекты Student и Course (как параметры метода или возвращаемые типы)

public class EnrollmentService {
    public void enroll(Student s, Course c){}
}

Ассоциация (has-a)
Это означает, что почти всегда существует связь между объектами (они связаны). Объект заказа имеет объект Customer

public class Order {
    private Customer customer
}

Агрегация (has-a + whole-part)
Специальный вид ассоциации, в которой существует отношение целых частей между двумя объектами. они могут жить друг без друга, хотя.

public class PlayList{
    private List<Song> songs;
}

Примечание: самая сложная часть - отличить агрегацию от обычной ассоциации. Честно говоря, я думаю, что это открыто для разных интерпретаций.

Состав (has-a + целое-часть + владение)
Специальный вид агрегации. An Apartmentсостоит из некоторых Rooms. А Roomне может существовать без Apartment. при удалении квартиры удаляются также все связанные комнаты.

public class Apartment{
    private Room bedroom;
    public Apartment() {
       bedroom = new Room();
    }
}

1
Да, единственная сложная часть в определении объектных отношений - это различие между Ассоциацией и Агрегацией. Все остальное понятно. +1 от меня
Фуад Букредин

28

Из поста Роберта Мартина в comp.object :

Ассоциация представляет способность одного экземпляра отправить сообщение другому экземпляру. Обычно это реализуется с помощью указателя или ссылочной переменной экземпляра, хотя это также может быть реализовано как аргумент метода или создание локальной переменной.

//[Example:]

//|A|----------->|B|

class A
{
  private:
    B* itsB;
};

Агрегация [...] является типичным отношением цельное / частичное. Это то же самое, что и ассоциация, за исключением того, что экземпляры не могут иметь отношения циклического агрегирования (т. Е. Часть не может содержать свое целое).

//[Example:]

//|Node|<>-------->|Node|

class Node
{
  private:
    vector<Node*> itsNodes;
};

Тот факт, что это агрегация, означает, что экземпляры Node не могут образовывать цикл. Таким образом, это дерево узлов, а не граф узлов.

Композиция [...] точно такая же, как Агрегация, за исключением того, что время жизни «части» контролируется «целым». Этот контроль может быть прямым или переходным. То есть «целое» может взять на себя прямую ответственность за создание или уничтожение «части», или оно может принять уже созданную часть, а затем передать ее какому-то другому целому, которое берет на себя ответственность за нее.

//[Example:]

//|Car|<#>-------->|Carburetor|

class Car
{
  public:
    virtual ~Car() {delete itsCarb;}
  private:
    Carburetor* itsCarb
};

1
Насколько авторитетно это определение? Поддерживается ли это авторами стандарта UML? Я это поддерживал инструментами?
reinierpost

1
Это Роберт С. Мартин. Это достаточно авторитет для меня :-)
Heliac

21

Как говорили другие, ассоциация - это связь между объектами, агрегация и композиция - это типы ассоциации.

С точки зрения реализации агрегация получается с помощью ссылки на класс . Например, если класс A агрегирует объект класса B, у вас будет что-то вроде этого (в C ++):

class A {
    B & element;
  // or B * element;
};

Семантика агрегации заключается в том, что когда объект A уничтожается, объект B, который он хранит, все еще существует. При использовании композиции у вас более сильные отношения, обычно путем сохранения члена по значению :

class A {
    B element;
};

Здесь, когда объект A уничтожается, объект B, который он содержит, также будет уничтожен. Самый простой способ добиться этого - сохранить член по значению, но вы также можете использовать некоторый умный указатель или удалить член в деструкторе:

class A {
    std::auto_ptr<B> element;
};

class A {
    B * element;

    ~A() {
        delete B;
    }
};

Важным моментом является то, что в композиции контейнерному объекту принадлежит содержащийся в нем объект , а при агрегации он ссылается на него.


8
Это должен быть единственный принятый ответ. Композиция не существует в C # и Java, за исключением примитивных типов ... Тем не менее, вы видите разработчиков этих языков, "объясняющих" композицию. Композиция означает, что объект существует ВНУТРИ другого. В Java и C # вы даже не можете этого сделать, все находится в куче, и вы просто держите указатель на него, это действительно агрегация, а не композиция. C ++ обеспечивает композицию ..
Все

14

Удивительно, как много путаницы существует в отношении различия между тремя понятиями отношений: объединение , агрегация и состав. .

Обратите внимание, что термины агрегация и состав использовались в сообществе C ++, возможно, в течение некоторого времени, прежде чем они были определены как особые случаи ассоциации в диаграммах классов UML.

Основная проблема заключается в широко распространенном и постоянном недоразумении (даже среди опытных разработчиков программного обеспечения), что концепция композиции подразумевает зависимость жизненного цикла между целым и его частями, так что части не могут существовать без целого, игнорируя тот факт, что существуют также случаи ассоциаций части-целого с частями, не предназначенными для совместного использования, когда части можно отделить от целого и пережить его уничтожение.

Насколько я понимаю, эта путаница имеет два корня:

  1. В сообществе C ++ термин «агрегация» использовался в смысле класса, определяющего атрибут для ссылки на объекты другого независимого класса (см., Например, [1]), что является смыслом ассоциации в диаграммах классов UML. Термин «композиция» использовался для классов, которые определяют объекты-компоненты для своих объектов, так что при уничтожении составного объекта эти объекты-компоненты также уничтожаются.

  2. В диаграммах классов UML и «агрегация», и «композиция» были определены как особые случаи ассоциаций, представляющих отношения часть-целое (которые долгое время обсуждались в философии). В их определениях различие между «агрегацией» и «композицией» основано на том факте, позволяет ли оно разделять часть между двумя или более целыми. Они определяют «композиции» как имеющие не разделяемые (исключительные) части, в то время как «агрегаты» могут делиться своими частями. Кроме того, они говорят что-то вроде следующего: очень часто, но не во всех случаях, композиции имеют зависимость жизненного цикла между целым и его частями, так что части не могут существовать без целого.

Таким образом, хотя UML поместил термины «агрегация» и «композиция» в правильный контекст (отношения «часть-целое»), им не удалось дать им четкое и однозначное определение, охватывающее интуицию разработчиков. Тем не менее, это не удивительно, поскольку существует множество свойств (и нюансов реализации), которые могут иметь эти отношения, и разработчики не договариваются о том, как их реализовать.

Смотрите также мой расширенный ответ на вопрос SO от апреля 2009 года, указанный ниже.

И свойство, которое, как предполагалось, определяет «композицию» между объектами ООП в сообществе C ++ (и это убеждение все еще широко распространено): зависимость жизненного цикла во время выполнения между двумя связанными объектами (составной и ее компонент) не совсем характерно для «композиции», потому что мы можем иметь такие зависимости из-за ссылочной целостности и в других типах ассоциаций.

Например, следующий кодовый код для «композиции» был предложен в ответе SO :

final class Car {    
  private final Engine engine;

  Car(EngineSpecs specs) {
    engine = new Engine(specs);
  }

  void move() {
    engine.work();
  }
}

Респондент утверждал, что для «состава» было бы характерно, чтобы никакой другой класс не мог ссылаться на компонент или знать его. Однако это, безусловно, не относится ко всем возможным случаям «композиции». В частности, в случае двигателя автомобиля, производитель автомобиля, возможно, реализованный с помощью другого класса, может ссылаться на двигатель, чтобы иметь возможность связаться с владельцем автомобиля всякий раз, когда возникает проблема с ним.

[1] http://www.learncpp.com/cpp-tutorial/103-aggregation/

Приложение - неполный список часто задаваемых вопросов о композиции и агрегации в StackOverflow

[ Апр 2009 ]
Агрегация против Композиции [закрыто как основанная главным образом на мнении]
[ Апр 2009 ] В
чем разница между Композицией и Ассоциацией?
[ Май 2009 ]
Разница между объединением, агрегацией и составом
[ май 2009 ] В
чем разница между составом и агрегацией? [дубликаты]
[ октябрь 2009 г. ] В
чем разница между агрегацией, составом и зависимостью? [помечено как дубликат]
[ ноябрь 2010 ]
Ассоциация против агрегации [помечено как дубликат]
[Август 2012 ]
Разница в реализации между агрегацией и композицией в Java
[ февраль 2015 ]
UML - ассоциация или агрегация (простые фрагменты кода)


upvote за неполный список часто задаваемых вопросов.
Jacco

13

ассоциация

Ассоциация представляет отношения между двумя классами. Она может быть однонаправленной (односторонней) или двунаправленной (двухсторонней)

например:

  1. однонаправленный

Заказчик размещает заказы

  1. двунаправленный

А женат на Б

Б женат на А

агрегирование

Агрегация - это своего рода ассоциация. Но со специфическими особенностями. Агрегация - это отношение в одном большем «целом» классе, содержащем один или несколько меньших классов «частей». И наоборот, меньший класс «part» является частью «целого» более крупного класса ,

например:

в клубе есть члены

Клуб («целый») состоит из нескольких членов клуба («частей»). У члена есть жизнь вне клуба. Если бы клуб («целый») умер, члены («части») не умерли бы с ним. Потому что член может принадлежать нескольким клубам («целым»).

Сочинение

Это более сильная форма агрегации. «Целое» отвечает за создание или уничтожение своих «частей»

Например:

Школа имеет отделы

В этом случае школа («целое») должна была умереть, отдел («части») умрет с этим. Потому что каждая часть может принадлежать только одному «целому».


В случае соглашения. Должен ли я использовать class Club(){ _member = new Member } или передать его в качестве ссылкиclass Club(){ addMember(Member member) { this._member = member } }
бросьте

12

Важно понять, почему мы должны беспокоиться об использовании более одного раза линии отношений. Наиболее очевидная причина заключается в описании отношений родитель-потомок между классами (когда родитель удалял все дочерние элементы удаляются в результате), но, что более важно, мы хотим различать простую ассоциацию и композицию, чтобы наложить неявные ограничения на видимость и распространение изменений в связанных классах, вопрос, который играет важную роль в понимании и уменьшении сложности системы.

ассоциация

Наиболее абстрактный способ описать статические отношения между классами - это использовать ссылку «Ассоциация», которая просто утверждает, что существует какая-то связь или зависимость между двумя классами или более.

Слабая Ассоциация

ClassA может быть связан с ClassB для того, чтобы показать, что один из его методов включает параметр экземпляра ClassB или возвращает экземпляр ClassB.

Сильная Ассоциация

ClassA также может быть связан с ClassB, чтобы показать, что он содержит ссылку на экземпляр ClassB.

Агрегация (Общая Ассоциация)

В тех случаях, когда между ClassA (целым) и ClassB (частичным) существует частичная связь, мы можем быть более конкретными и использовать ссылку агрегации вместо ссылки ассоциации, подчеркивая, что ClassB также может агрегироваться другими классами в приложении ( поэтому агрегация также называется общей ассоциацией).

введите описание изображения здесь

Важно отметить, что ссылка агрегации никоим образом не говорит о том, что ClassA владеет ClassB, и что между ними есть родительско-дочерние отношения (когда родитель удалил все дочерние элементы, которые в результате удаляются). На самом деле, совсем наоборот! Ссылка агрегации обычно используется для подчеркивания того факта, что ClassA не является эксклюзивным контейнером ClassB, поскольку на самом деле ClassB имеет другой контейнер.

Агрегация против Ассоциации Ссылка ассоциации может заменить ссылку агрегации в любой ситуации, в то время как агрегация не может заменить ассоциацию в ситуациях, когда между классами есть только «слабая связь», то есть ClassA имеет методы, которые содержат параметр ClassB, а ClassA не хранить ссылку на экземпляр ClassB.

Мартин Фаулер предполагает, что ссылка агрегации вообще не должна использоваться, потому что она не имеет добавленной стоимости и нарушает согласованность, цитируя Джима Рамбо «Думайте об этом как о плацебо для моделирования».

Композиция (Не разделяемая ассоциация)

Мы должны быть более конкретными и использовать составную ссылку в тех случаях, когда в дополнение к частичной взаимосвязи между ClassA и ClassB - между ними существует сильная зависимость жизненного цикла, что означает, что когда ClassA удаляется, ClassB также удаляется в результате

введите описание изображения здесь

Ссылка на композицию показывает, что класс (контейнер, целое) обладает исключительным владением другим классом (частями), что означает, что объект контейнера и его части составляют отношения родитель-потомок.

В отличие от ассоциации и агрегации, при использовании отношения составления составной класс не может отображаться как тип возвращаемого значения или тип параметра составного класса. Таким образом, изменения в составленном классе не могут распространяться на остальную часть системы. Следовательно, использование композиции ограничивает рост сложности по мере роста системы.

Измерение сложности системы

Сложность системы можно измерить, просто взглянув на диаграмму классов UML и оценив линии связей, агрегации и композиции. Способ измерения сложности состоит в определении количества классов, на которые может повлиять изменение определенного класса. Если класс A представляет класс B, то на любой данный класс, который использует класс A, теоретически могут повлиять изменения в классе B. Сумма числа потенциально затронутых классов для каждого класса в системе представляет собой общую сложность системы.

Вы можете прочитать больше в моем блоге: http://aviadezra.blogspot.com/2009/05/uml-association-aggregation-composition.html



Хороший ответ. 1) Вопрос к композиционному примеру: Ленг и Хэнд (композиция) Персона. если я создаю класс Animal и Sleep, то Sleep (agregation) Person; Сон (агрегат) Животное. Это правильно? 2). Ручной состав Person: class Person() { private hand = new Hand }. Соглашение о сне Лицо class Person() { private sleep = new Sleep }Действительно ли использовать ключ «новый» в Сне? или я должен передать это как ссылку, потому что это соглашение? class Person() { private Sleep _sleep; public addSleep(Sleep sleep) { this._sleep = sleep} }
ролл

7

Композиция (при удалении «целого» «часть» также удаляется автоматически - «Владение»)

  • Создайте объекты вашего существующего класса внутри нового класса. Это называется композицией, потому что новый класс состоит из объектов существующих классов.

  • Обычно используют обычные переменные-члены.

  • Может использовать значения указателя, если составной класс автоматически обрабатывает распределение / освобождение, ответственное за создание / уничтожение подклассов.

введите описание изображения здесь

Композиция в C ++

#include <iostream>
using namespace std;
/********************** Engine Class ******************/
class Engine
{
    int nEngineNumber;
    public:
    Engine(int nEngineNo);
    ~Engine(void);
};
Engine::Engine(int nEngineNo)
{
    cout<<" Engine :: Constructor " <<endl;
}
Engine::~Engine(void)
{
    cout<<" Engine :: Destructor " <<endl;
}
/********************** Car Class ******************/
class Car
{
    int nCarColorNumber;
    int nCarModelNumber;
    Engine objEngine;
    public:
    Car (int, int,int);
    ~Car(void);
};
Car::Car(int nModelNo,int nColorNo, int nEngineNo):
nCarModelNumber(nModelNo),nCarColorNumber(nColorNo),objEngine(nEngineNo)
{
    cout<<" Car :: Constructor " <<endl;
}
Car::~Car(void)
{
    cout<<" Car :: Destructor " <<endl;
    Car
    Engine
    Figure 1 : Composition
}
/********************** Bus Class ******************/
class Bus
{
    int nBusColorNumber;
    int nBusModelNumber;
    Engine* ptrEngine;
    public:
    Bus(int,int,int);
    ~Bus(void);
};
Bus::Bus(int nModelNo,int nColorNo, int nEngineNo):
nBusModelNumber(nModelNo),nBusColorNumber(nColorNo)
{
    ptrEngine = new Engine(nEngineNo);
    cout<<" Bus :: Constructor " <<endl;
}
Bus::~Bus(void)
{
    cout<<" Bus :: Destructor " <<endl;
    delete ptrEngine;
}
/********************** Main Function ******************/
int main()
{
    freopen ("InstallationDump.Log", "w", stdout);
    cout<<"--------------- Start Of Program --------------------"<<endl;
    // Composition using simple Engine in a car object
    {
        cout<<"------------- Inside Car Block ------------------"<<endl;
        Car objCar (1, 2,3);
    }
    cout<<"------------- Out of Car Block ------------------"<<endl;
    // Composition using pointer of Engine in a Bus object
    {
        cout<<"------------- Inside Bus Block ------------------"<<endl;
        Bus objBus(11, 22,33);
    }
    cout<<"------------- Out of Bus Block ------------------"<<endl;
    cout<<"--------------- End Of Program --------------------"<<endl;
    fclose (stdout);
}

Вывод

--------------- Start Of Program --------------------
------------- Inside Car Block ------------------
Engine :: Constructor
Car :: Constructor
Car :: Destructor
Engine :: Destructor
------------- Out of Car Block ------------------
------------- Inside Bus Block ------------------
Engine :: Constructor
Bus :: Constructor
Bus :: Destructor
Engine :: Destructor
------------- Out of Bus Block ------------------
--------------- End Of Program --------------------

Агрегация (если вы удалите «целое», «Часть» может существовать - «Нет собственности»)

  • Агрегация - это особый тип композиции, где не подразумевается право собственности между сложным объектом и подобъектами. Когда агрегат уничтожается, подобъекты не уничтожаются.

  • Обычно используют переменные-указатели / ссылочные переменные, которые указывают на объект, который находится вне области действия агрегатного класса.

  • Может использовать ссылочные значения, которые указывают на объект, который находится за пределами области действия агрегатного класса.

  • Не несет ответственности за создание / уничтожение подклассов

введите описание изображения здесь

Код агрегации в C ++

#include <iostream>
#include <string>
using namespace std;
/********************** Teacher Class ******************/
class Teacher
{
    private:
    string m_strName;
    public:
    Teacher(string strName);
    ~Teacher(void);
    string GetName();
};
Teacher::Teacher(string strName) : m_strName(strName)
{
    cout<<" Teacher :: Constructor --- Teacher Name :: "<<m_strName<<endl;
}
Teacher::~Teacher(void)
{
    cout<<" Teacher :: Destructor --- Teacher Name :: "<<m_strName<<endl;
}
string Teacher::GetName()
{
    return m_strName;
}
/********************** Department Class ******************/
class Department
{
    private:
    Teacher *m_pcTeacher;
    Teacher& m_refTeacher;
    public:
    Department(Teacher *pcTeacher, Teacher& objTeacher);
    ~Department(void);
};
Department::Department(Teacher *pcTeacher, Teacher& objTeacher)
: m_pcTeacher(pcTeacher), m_refTeacher(objTeacher)
{
    cout<<" Department :: Constructor " <<endl;
}
Department::~Department(void)
{
    cout<<" Department :: Destructor " <<endl;
}
/********************** Main Function ******************/
int main()
{
    freopen ("InstallationDump.Log", "w", stdout);
    cout<<"--------------- Start Of Program --------------------"<<endl;
    {
        // Create a teacher outside the scope of the Department
        Teacher objTeacher("Reference Teacher");
        Teacher *pTeacher = new Teacher("Pointer Teacher"); // create a teacher
        {
            cout<<"------------- Inside Block ------------------"<<endl;
            // Create a department and use the constructor parameter to pass the teacher to it.
            Department cDept(pTeacher,objTeacher);
            Department
            Teacher
            Figure 2: Aggregation
        } // cDept goes out of scope here and is destroyed
        cout<<"------------- Out of Block ------------------"<<endl;
        // pTeacher still exists here because cDept did not destroy it
        delete pTeacher;
    }
    cout<<"--------------- End Of Program --------------------"<<endl;
    fclose (stdout);
}

Вывод

--------------- Start Of Program --------------------
Teacher :: Constructor --- Teacher Name :: Reference Teacher
Teacher :: Constructor --- Teacher Name :: Pointer Teacher
------------- Inside Block ------------------
Department :: Constructor
Department :: Destructor
------------- Out of Block ------------------
Teacher :: Destructor --- Teacher Name :: Pointer Teacher
Teacher :: Destructor --- Teacher Name :: Reference Teacher
--------------- End Of Program --------------------

Кто бы ни отрицал, проголосовал за этот ответ. Не могли бы вы объяснить причину, по которой вы проголосовали?
Саураб Раот

Что меня действительно смущает, так это то, что во многих случаях владелец удерживает не вещь, а принадлежащую ей вещь, которая удерживает владельца. Например, у автомобиля нет указателя типа Engine *, но в классе Engine есть член типа Car для хранения принадлежащего ему автомобиля. Я не совсем понимаю, особенно отношения между классами в этом случае.
Дуду

6

Проблема с этими ответами состоит в том, что они - половина истории: они объясняют, что агрегация и состав являются формами ассоциации, но они не говорят, возможно ли объединение быть ни тем, ни другим.

Основываясь на некоторых кратких чтениях многих постов по SO и некоторых документах UML, я понял, что существует 4 основных конкретных формы ассоциации классов:

  1. состав: А состоит из А; Б не существует без А, как комната в доме
  2. агрегация: A имеет-A B; Б может существовать без А, как ученик в классе
  3. зависимость: A использует-a B; нет зависимости жизненного цикла между A и B, как параметр вызова метода, возвращаемое значение или временный объект, созданный во время вызова метода
  4. обобщение: A is-a B

Когда отношения между двумя объектами не являются одним из них, их можно просто назвать «ассоциацией» в общем смысле этого термина и далее описать другими способами (примечание, стереотип и т. Д.).

Я предполагаю, что «общая ассоциация» предназначена для использования в основном в двух обстоятельствах:

  • когда специфика отношений все еще прорабатывается; такие отношения в диаграмме должны быть как можно скорее преобразованы в то, чем они на самом деле являются / будут (один из других 4).
  • когда отношение не совпадает ни с одним из этих 4, определенных UML; «универсальная» ассоциация все еще дает вам способ представления отношения, которое «не одно из других», так что вы не застряли, используя неправильные отношения с примечанием «это на самом деле не агрегация, это просто UML нет другого символа, который мы могли бы использовать

1
Как именно вы реализуете обобщенную ассоциацию, если исключены все остальные опции? Если A не состоит из B (значение B находится в A), A не является агрегацией B (ссылка B не находится в A), B не наследуется / не реализуется из A, а B не используется в качестве возврата, параметра или внутри использование функции A, вы в значительной степени остались без отношения вообще.
Дин Р

1
@DeanP В настоящее время он может быть просто общим, а затем будет преобразован в один из 4 (тогда он станет реализуемым); ИЛИ это могут быть отношения, которые не вписываются в 4, например, если вы хотите ассоциацию, которая означает «выглядит», без общей ассоциации вы будете вынуждены использовать одну из 4, что вводит читателя в заблуждение, тогда как если вы используете Вообще, вы, скорее всего, будете комментировать его или ставить заметку, объясняющую, что это такое, и большинство людей читают заметки, только если не понимают символ;)
Оливер

5

Я думаю, что эта ссылка сделает вашу домашнюю работу: http://ootips.org/uml-hasa.html

Чтобы понять термины, я помню пример в мои первые дни программирования:

Если у вас есть объект «шахматная доска», который содержит объекты «коробки», который является композицией потому что, если «шахматная доска» удалена, больше нет причин для существования блоков.

Если у вас есть «квадратный» объект, который имеет «цветной» объект, и квадрат удаляется, «цветной» объект все еще может существовать, то есть агрегация

Оба они являются ассоциациями , главное отличие - концептуальное.


5

Композиция : это когда вы уничтожаете объект (школу), другой объект (классные комнаты), который привязан к нему, тоже будет уничтожен. Оба они не могут существовать независимо.

Агрегация : Это своего рода полная противоположность Compositionассоциации выше ( ), где, когда вы убиваете объект ( Company), другой объект ( Employees), связанный с ним, может существовать сам по себе.

Ассоциация .
Состав и агрегация - это две формы ассоциации.


1
Строго говоря, сотрудники компании не могут существовать без компании. Это правда, что вы не убиваете людей, но они больше не являются сотрудниками этой компании. Таким образом, я думаю, что лучшая аналогия была бы с Отделением и Сотрудниками, где, даже если отделение закрывается, они могли бы продолжать быть сотрудниками компании.
Александр

1
да, абсолютно. Согласен ... +1 Спасибо @AlexPopov за то, что указал на это. :)
Куласангар,

4
    Simple rules:
    A "owns" B = Composition : B has no meaning or purpose in the system 
    without A
    A "uses" B = Aggregation : B exists independently (conceptually) from A
    A "belongs/Have" B= Association; And B exists just have a relation
    Example 1:

    A Company is an aggregation of Employees.
    A Company is a composition of Accounts. When a Company ceases to do 
    business its Accounts cease to exist but its People continue to exist. 
    Employees have association relationship with each other.

    Example 2: (very simplified)
    A Text Editor owns a Buffer (composition). A Text Editor uses a File 
    (aggregation). When the Text Editor is closed,
    the Buffer is destroyed but the File itself is not destroyed.

3

В очень простом предложении:
Агрегация и Композиция являются подмножествами ассоциации.

  • A использует B -> это агрегация

  • A нуждается B -> это композиция.

Узнайте больше здесь .


2

Я хотел бы проиллюстрировать, как три термина реализованы в Rails. ActiveRecord вызывает любой тип отношений между двумя моделями association. Не нашел бы очень часто термины compositionи aggregation, при чтении документации или статьи, связанные с ActiveRecord. Ассоциация создается путем добавления одного из макросов класса ассоциации в тело класса. Некоторые из этих макросов belongs_to, has_oneи has_manyт. Д ..

Если мы хотим установить compositionили aggregation, нам нужно добавить belongs_toк собственной модели (также называемой дочерней) и has_oneили has_manyк модели-владельцу (также называемой родительской). Настроены ли мы compositionили aggregationзависит от параметров, которые мы передаем belongs_toвызову в дочерней модели. До Rails 5, установка belongs_toбез каких-либо опций создала aggregation, потомок мог существовать без родителя. Если мы хотели composition, нам нужно было явно объявить это, добавив параметр required: true:

class Room < ActiveRecord::Base
  belongs_to :house, required: true
end

В Rails 5 это было изменено. Теперь, объявление belongs_toассоциации создает compositionпо умолчанию, дочерний элемент не может существовать без родителя. Таким образом, приведенный выше пример можно переписать так:

class Room < ApplicationRecord
  belongs_to :house
end

Если мы хотим позволить дочернему объекту существовать без родителя, нам нужно объявить это явно через опцию optional

class Product < ApplicationRecord
  belongs_to :category, optional: true
end

2

Из книги Ремо Х. Янсена «Начало реакции: изучение TypeScript 2.x - второе издание»:

Мы называем ассоциацию те отношения, чьи объекты имеют независимый жизненный цикл, в котором нет собственности на объекты. Давайте посмотрим на пример учителя и ученика. Несколько учеников могут быть связаны с одним учителем, а один ученик может быть связан с несколькими учителями, но оба имеют независимые жизненные циклы (оба могут создавать и удалять независимо). Поэтому, когда учитель покидает школу, нам не нужно удалять учеников, а когда ученик покидает школу, нам не нужно удалять учителей.

Мы называем агрегацию теми отношениями, чьи объекты имеют независимый жизненный цикл, но есть владение, и дочерние объекты не могут принадлежать другому родительскому объекту. Давайте рассмотрим пример сотового телефона и аккумулятора сотового телефона. Одна батарея может принадлежать телефону, но если телефон перестает работать, и мы удаляем его из нашей базы данных, батарея телефона не будет удалена, поскольку она все еще может функционировать. Таким образом, в совокупности, пока существует собственность, объекты имеют свой жизненный цикл

Мы используем термин состав для обозначения отношений, чьи объекты не имеют независимого жизненного цикла, и если родительский объект будет удален, все дочерние объекты также будут удалены. Давайте рассмотрим пример взаимосвязи между вопросами и ответами. Отдельные вопросы могут иметь несколько ответов, и ответы не могут принадлежать нескольким вопросам. Если мы удалим вопросы, ответы будут автоматически удалены.


1

ассоциация - это связь между двумя отдельными классами, и ассоциация может быть любого типа, скажем, один к одному, один к мая и т. Д. Она объединяет две совершенно разные сущности.

агрегирование - это особая форма ассоциации, которая представляет собой однонаправленные односторонние отношения между классами (или объектами), например, для классов Wallet и Money. У кошелька есть деньги, но деньги не обязательно должны быть у кошелька, так что это однонаправленные отношения. В этом отношении обе записи могут выжить, если другая заканчивается. В нашем примере, если класс Wallet отсутствует, это не означает, что класс Money не может существовать.

Композиция - это ограниченная форма агрегации, в которой две сущности (или, можно сказать, классы) сильно зависят друг от друга. Например, для человека и сердца. Человеку нужно сердце, чтобы жить, а сердцу нужно человеческое тело, чтобы выжить. Другими словами, когда классы (сущности) зависят друг от друга и их продолжительность жизни одинакова (если один умирает, то и другой тоже), тогда это композиция. Класс сердца не имеет смысла, если класса Человека нет.


1

https://www.linkedin.com/pulse/types-relationships-object-oriented-programming-oop-sarah-el-dawody/

Композиция: является частью отношений.

например, «двигатель - это часть автомобиля», «сердце - это часть тела».

введите описание изображения здесь

Ассоциация: это отношение типа «есть»

Например, предположим, что у нас есть два класса, тогда эти два класса называются отношениями «имеет», если оба эти объекта совместно используют объект друг друга для некоторой работы, и в то же время они могут существовать без зависимости друг от друга или оба имеют свои собственная жизнь

введите описание изображения здесь

Приведенный выше пример демонстрирует отношения ассоциации, поскольку класс Employee и Manager используют объект друг друга и оба имеют свой независимый жизненный цикл.

Агрегация: основана на отношениях "есть-а" и является специальной формой ассоциации

например, «Студент» и «адрес». У каждого учащегося должен быть адрес, поэтому отношения между классом ученика и классом адреса будут иметь тип отношения «Has-A», но наоборот это не так.

введите описание изображения здесь

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.