Object-Oriented Analysis Design learning and exploration (6): good design = software flexibility (good design = flexible software)

Source: Internet
Author: User

Changes are inevitable. No matter how much you appreciate your software. It may change tomorrow, and it may be difficult to change. This will be reflected in the customer's demand changes. In this chapter, visit an old friend to improve the existing system, and see how to solve large problems with less changes.

Do you still remember the boss of the guitar store? We developed a guitar query system. As the business grows better, he wants to start mandolin's business, but the existing system cannot query this instrument.

We talked a lot about "good analytical design is the key to software reuse and expansion". Now let's take a look at how to make relatively simple changes.ProgramSo that the program can support mandolin queries. First, let's look at the class diagram of the original query tool:

How can we add new instruments to the query tool? Actually, let's look at the instrument. There are many similarities with the guitar. We can abstract an interface or we can make an abstract type.

Note: The abstract type is actually a placeholder for The Implementation type or derived type (abstract classes are placeholders for actual implementation classes). The abstract type defines the behavior, and the derived type implements these actions (the abstract class defines behavior, and the subclasses implement that behavior ). Whenever you see a public behavior in one or more places, be sure to abstract this behavior to a type, and use these actions in the public type (whenever you find common behavior in two or more places, look to abstract that behavior in a class, and then reuse that behavior in the common classes ).

Mandolin is similar to the guitar, but there are still some differences. mandolin has a style attribute, and most mandolin has four strings. For mandolin, the number of strings is unnecessary. Of course, like a guitar, mandolin also needs a mandolinspec type.

Now, we put all types together to form a system type diagram:

Now let's look at the encoding:

Public abstract class Instrument

{

Private string _ serialnumber;

Private double _ price;

Private instrumentspec _ spec;

Public String serialnumber

{

Get {return _ serialnumber ;}

Set {_ serialnumber = value ;}

}

Public double price

{

Get {return _ price ;}

Set {_ price = value ;}

}

Public instrumentspec spec

{

Get {return _ spec ;}

Set {_ spec = value ;}

}

Public instrument (string serialnumber, double price, instrumentspec spec)

{

_ Serialnumber = serialnumber;

_ Price = price;

_ Spec = spec;

}

Public instrumentspec getspec ()

{

Return _ spec;

}

}

Public abstract class instrumentspec

{

Private string _ builder;

Private string _ model;

Private string _ type;

Private string _ backwood;

Private string _ topwood;

Public instrumentspec (string builder, string model, string type, string backwood, string topwood)

{

Builder = builder;

Model = model;

Type = type;

Backwood = backwood;

Topwood = topwood;

}

Public String Builder

{

Get {return _ builder ;}

Set {_ builder = value ;}

}

Public String Model

{

Get {return _ model ;}

Set {_ model = value ;}

}

Public string type

{

Get {return _ type ;}

Set {_ type = value ;}

}

Public String backwood

{

Get {return _ backwood ;}

Set {_ backwood = value ;}

}

Public String topwood

{

Get {return _ topwood ;}

Set {_ topwood = value ;}

}

Public Boolean matches (instrumentspec otherspec)

{

Boolean flag = true;

If (builder! = Otherspec. Builder)

Flag = false;

If (model! = Otherspec. Model)

Flag = false;

If (type! = Otherspec. type)

Flag = false;

If (backwood! = Otherspec. backwood)

Flag = false;

If (topwood! = Otherspec. topwood)

Flag = false;

Return flag;

}

}

Public class guitarspec: instrumentspec

{

Private int _ numstring;

Public int numstring

{

Get {return _ numstring ;}

Set {_ numstring = value ;}

}

Public guitarspec (string builder, string model, string type,

String backwood, string topwood, int numstring)

: Base (builder, model, type, backwood, topwood)

{

Numstring = numstring;

}

Public Boolean matches (instrumentspec spec)

{

Boolean flag = true;

If (! Base. Matches (SPEC ))

Flag = false;

If (! (Spec is guitarspec ))

Flag = false;

Else

{

If (guitarspec) SPEC). numstring! = Numstring)

Flag = false;

}

Return flag;

}

}

Public class guitar: Instrument

{

Public guitar (string serialnumber, double price, guitarspec spec)

: Base (serialnumber, price, spec)

{}

}

Public class mandolinspec: instrumentspec

{

Private string _ style;

Public String Style

{

Get {return _ style ;}

Set {_ style = value ;}

}

Public mandolinspec (string builder, string model, string type,

String backwood, string topwood, string style)

: Base (builder, model, type, backwood, topwood)

{

Style = style;

}

Public Boolean mathes (instrumentspec spec)

{

Boolean flag = true;

If (! Base. Matches (SPEC ))

Flag = false;

If (! (Spec is mandolinspec ))

Flag = false;

Else

{

If (mandolinspec) SPEC). style! = Style)

Flag = false;

}

Return flag;

}

}

Public class mandolin: Instrument

{

Public mandolin (string serialnumber, double price, mandolinspec spec)

: Base (serialnumber, price, spec)

{}

}

Public class inventory

{

Private list <instrument> _ inventory;

Public list <instrument> Inventory

{

Get {return _ inventory ;}

Set {_ inventory = value ;}

}

Public void addinventory (string serialnumber, double price, instrumentspec spec)

{

Instrument instrument = NULL;

If (spec is guitarspec)

Instrument = new guitar (serialnumber, price, (guitarspec) SPEC );

Else if (spec is mandolinspec)

Instrument = new mandolin (serialnumber, price, (mandolinspec) SPEC );

If (instrument! = NULL)

Inventory. Add (instrument );

}

Public instrument get (string serialnumber)

{

Instrument getinstrument = NULL;

Foreach (Instrument instrument in inventory)

{

If (instrument. serialnumber = serialnumber)

{

Getinstrument = instrument;

Break;

}

}

Return getinstrument;

}

Public list <mandolin> Search (mandolinspec spec)

{

List <mandolin> List = new list <mandolin> ();

Foreach (Instrument instrument in inventory)

{

If (instrument is mandolin)

{

If (instrument. getspec (). Matches (SPEC ))

List. Add (mandolin) instrument ));

}

}

Return list;

}

Public list <guitar> Search (guitarspec spec)

{

List <guitar> List = new list <guitar> ();

Foreach (Instrument instrument in inventory)

{

If (instrument is guitar)

{

If (instrument. getspec (). Matches (SPEC ))

List. Add (guitar) instrument ));

}

}

Return list;

}

}

Now let's test:

Class Program

{

Static inventory;

Static void main (string [] ARGs)

{

Inventoryinit ();

List <guitar> guitarlist = inventory. Search (New guitarspec ("builder1", "model1", "type1", "backwood1", "topwood1", 6 ));

If (guitarlist! = NULL)

{

Foreach (guitar in guitarlist)

{

Console. writeline ("Guitar's serialnumber is" + guitar. serialnumber );

}

}

List <mandolin> mandolinlist = inventory. Search (New mandolinspec ("builder3", "model3", "type3", "backwood3", "topwood3", "style1 "));

If (mandolinlist! = NULL)

{

Foreach (mandolin in mandolinlist)

{

Console. writeline ("mandolin's serialnumber is" + mandolin. serialnumber );

}

}

Console. Read ();

}

Public static void inventoryinit ()

{

Inventory = new inventory ();

Inventory. Inventory = new list <instrument> ();

Inventory. inventory. add (new guitar ("001", 100, new guitarspec ("builder1", "model1", "type1", "backwood1", "topwood1", 6 )));

Inventory. inventory. add (new guitar ("002", 123, new guitarspec ("builder2", "model2", "type2", "backwood2", "topwood2", 6 )));

Inventory. inventory. add (New mandolin ("003", 124, new mandolinspec ("builder3", "model3", "type3", "backwood3", "topwood3 ", "style1 ")));

}

}

The output result is:

 

The current program should be better than the original one, and the abstract type is avoided.CodeDuplicate copy of. The attributes encapsulated in the instrument type are separated from the spec type. Do you still remember to write the three steps of the software? Can this query tool be regarded as a good software? Let's take a look at the following questions:

1. Can the new query tool meet users' needs? Yes. It can be used to find guitar and mandolin instruments.

2. Is the object-oriented principle used, such as encapsulation, to avoid code copying and the software is easy to expand? Use encapsulation in the instrumentspec type to inherit the instrument and instrumentspec when developing the super-type

3. Can I simply reuse this program? Will a part of the change program need to be changed in many places? Is the module decoupled? This program is difficult. All modules are closely linked

The best way to test whether there is a good software design is to try to change

If your software is hard to change, the problem may occur when you want to improve the design. Now let's see if several instruments can be easily changed. If a new instrument is added to an existing program, we need to add a new instrument specification and add a new query method to inventory, which does not seem easy to change!

It seems that we still have a lot to do to write this query tool. Of course, it does not mean that the work that has been completed is not important. In many cases, we must improve our design to discover new problems. We have now implemented the object-oriented principle in this query tool. There is a new topic before we continue to improve our design: Object-oriented disaster.

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.