using Composite Pattern to count the number of peo

2019-05-24 11:21发布

I'm trying to make a Composite Pattern that counts the number of people in the world, the continent, the state... sorry no state but country my bad sorry

Here is the pattern that I follow:enter image description here

I did this:

enter image description here

but I am not sure it's right, because can I use leaf -> population ?

Because when I did Composite Pattern for PC so its (PC= component from PC will be Cabinet = composite, from Cabinet will be HDD= leaf and Motherboard = composite, from Motherboard will be RAM = leaf and CPU = leaf). What I want to say every leafs are different and in my diagram are same.

and you think I have something good at least.

Thank you for your answers :)

2条回答
Luminary・发光体
2楼-- · 2019-05-24 11:40

First of all, you should start with an analysis of your problem. So what is that you have and how is it related. So you have a World that consists of continents, where each continent consists of countries, where each country consists of regions. When doing such a OO Analysis, the nouns (here marked in bold) are candidates for your classes. And the relational terms give some indications howp the classes are related (marked italic).

So what can we see frmo this? There are some terms (called entities) that have some directly ordered hierarchical containment relations. But no relation in the kind that something can be seen as an element of the other type. This is an important information when thinking about how to inherit from each other; as the inherits relation can be seen a specialization, it doesnt make any sense here: a country is not a specific world and a world is not a specific country. Further, we see there are no bypasses, e.g. a contry is no direct part of the world. And no element can contain an element of its own type, e.g. no country contains a country.

enter image description here

So what can we learn from this brief analysis? We cannot formulate the problem as a composite without changing significant expressiveness (e.g. changing the intended hierarchy) or without introducing much additional complexity (e.g. by constraints).

And now in the second step, we develop a design out of the analysis results. How the design looks like at the end depends on what shall be done with the elements.

  1. Solution: In your example you can just add a calculatePopulation operation to any of the classes. As any class knows its parts and their types, this can directly be done by calling the calculatePopulation operation of the contained instances of the next element type. This would be the OO way in solving such problems, which is most likely the best way if there are no further constraints.

enter image description here

And to start it you just call calculatePopulation of your wold instance.

If you want to treat any kind of element in a unified way, you can create an abstract class or interface and let all the elements inherit from it/implement it. This class/interface declares the calculatePopulation operation. Whith that improved solution you can start with an arbitrary element of your hierarchy to calculate the population without taking care for what kind of element it is.

  1. Solution: When you want to have an algorithm that is not implemented inside of the class hierarchy and that is recursive. In that case you need an abstraction, such that you can handle all the elements in the same way, as the algorithm implementation shall not take care for too much of the details. Thus also let all the elements inherit from an abstact class that has an operation that provides the contained elements and an operation that provides the population, which is directly part of the element ( not transitive/indirectly as in the case before). So now you would have the situation that you have two clearly disticitve cases, first you have child element and no direct population and, second, you have no child elements and a direct population. But your traversal can ignore this.

enter image description here

Here you start it by calling your implementation (which is an other class) and passing the object of which you want to have to population.

There are further solutions, of course. But all of those using a composite just for this problem are very artificial, because it is by its concept recursive and your problem is not recursive (i.e. there is no element that can contain a element of the same type) and thus the composite is unsiateble or lets call it oversized.

查看更多
来,给爷笑一个
3楼-- · 2019-05-24 11:51

At least you do not need to have World, Continent, State, Region.

Only Composite with maybe a property type is needed to know if this is a Continent or a State or a Region.

State should be the leaf no ?

Think like an files tree: the number of levels is not defined, the pattern supports any depth number.

On State you get a method getPopulation which is defined also in Component as abstract and in Composite with a return -1 or infinite (a value meaning not implemented).

For me, the method getChild is needed on leaf and Component also. Without it, it is not possible to implement a recursive algorithm to navigate through the composite.

On leaf, it returns an empty list: this the way to know that a leaf is reached.

enter image description here

PS : I leave the aggregation because it is used in your first diagram, if i do it i would use a simple association or a composition but not an aggreation.

查看更多
登录 后发表回答