From mboxrd@z Thu Jan 1 00:00:00 1970 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on polar.synack.me X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00 autolearn=ham autolearn_force=no version=3.4.4 X-Google-Language: ENGLISH,ASCII-7-bit X-Google-Thread: fac41,2c6139ce13be9980 X-Google-Attributes: gidfac41,public X-Google-Thread: f43e6,2c6139ce13be9980 X-Google-Attributes: gidf43e6,public X-Google-Thread: 103376,3d3f20d31be1c33a X-Google-Attributes: gid103376,public X-Google-Thread: 1108a1,2c6139ce13be9980 X-Google-Attributes: gid1108a1,public From: paul.johnson@gecm.com (Paul Johnson) Subject: Re: Interface/Implementation (was Re: Design by Contract) Date: 1997/09/03 Message-ID: <5uj6kq$edq$1@miranda.gmrc.gecm.com> X-Deja-AN: 269673499 References: <01bcb389$24f579d0$1c10d30a@ntwneil> <5u62es$e23$7@miranda.gmrc.gecm.com> <340C85CE.6F42@link.com> Organization: GEC-Marconi Research Centre Newsgroups: comp.object,comp.software-eng,comp.lang.ada,comp.lang.eiffel Date: 1997-09-03T00:00:00+00:00 List-Id: In article <340C85CE.6F42@link.com>, smize@link.com says... >I'm not familiar with Eiffel. Let me tell you a few things we >do in Ada, and you can tell me if the [Eiffel] tools support it or not. >Some capabilities that are provided by Ada's separate spec/body >approach are: >* Different order of subprograms -- one order or grouping may be > most meaningful for the interface, another for implementation. First, I'm not convinced that this *is* all that good a practice. Given a big package body in Ada, I'd expect to use the spec as a table of contents. Having things in a different order would be confusing and difficult. However I suppose a good browsing editor would solve this. Eiffel allows you to group features in 1 or more "feature" clauses. Partly this is done to specify export restrictions (features in each clause are exported as a group), and partly for ordering. The "short-flat" interface extractor keeps each "feature" clause together, but sorts the contents into alphabetical order. I think the "flat" part (ancestor importation) merges feature clauses with matching comments as well. So if I have a class and descendant which both contain feature -- Attributes Then these two feature clauses will be merged. Of course all this is implementation dependent, and any short-flat filter could support a gazillion options for tuning it. (My experience is mostly with the ISE environment). >* Unexported (local to the package) subprograms and declarations. Mixed. Any Eiffel class can have private routines and attributes, and most do. However there is no way that a class can be rendered "private" to the cluster, because "cluster" is much more an implementation issue than a language issue. Also, a descendant class can access all of its ancestor's features, including the private ones. Whether this is a Good Thing is debated. For a defence of this position, see OOSC2 by Bertrand Meyer. The objection is that if a class implementation is changed it might break unknown descendants. Design rules can help solve this problem. See Dejanews for a fairly recent discussion of this problem on c.l.e. >* Different comments -- the Ada spec usually contains comments that > describe what facility a subprogram provides and how to use it, > the package contains a description of its implementation details. Not a problem. Here is a feature declaration that does this: foo is -- This is the public comment for the short-flat interface. do -- Here is some private commentary about the implementation. end; And of course the comments on private features will not be included in the short-flat interface anyway. >* Interface control and verification -- the Ada spec can be written > and published, and other groups can code against it. If the > implementation or the client changes, the compiler can verify that > they are still consistent without having to reprocess both. This really asks two questions. One is about configuration management, and the other about incremental compilation. >From the configuration POV, the short-flat form can be generated and put under change control. If a class is modified then the short-flat form can be regenerated and compared with the controlled version. Also most of the environments (all?) can generate the short-flat form in HTML, which makes a very neat publication format. Incremental compilation is another matter, which I'm not going to address here because I don't know enough. >* Multiple interfaces -- you can have several sub-packages that > export subsets of a package's functionality. In Ada 83, if > visibility into the body (implementation) is required, these > must all be contained in the main package's spec; in Ada 95, > they can be separate child packages. In either case, if you > just want to re-package existing functionality to provide > different views, you can provide "view" packages that rename > elements from the main ("full-view") package. You can do this in Eiffel by using inheritance. The most common idiom is to create several "deferred" classes and then inherit these in various combinations to create the right interfaces. You can also inherit from an existing class and export a subset of its interface, but this is a rather dirty approach. Better (if possible) to make the new class a "sibling" which shares some of the same deferred ancestors. >* Multiple implementations, global, compile time -- you can have > many implementations of your package spec, and select the best > one for your application at compile time. Thus, your "list" > could have a hash table for faster lookup, or store its contents > to disk to allow long lists of huge data items (just one in > memory at a time), or whatever -- as long as the spec stays the > same, the client code doesn't need to be recompiled. Yup. Eiffel does this in the "ACE" file, which is implementation dependant. >* Multiple implementations, item-specific, compile time -- > Ada generics can provide a unified interface for several > implementations of a facility. Any logic that is common across > all the implementations is written into the generic, while any > code that is implementation-specific is provides as subprograms > that are parameters to the generic. In the worst case, the > generic only provides a "template" that instantiations must > follow. For example: > > generic > type Item is private; > type Stack is private; > with procedure Push (S: in out Stack; I: in out Item); > with procedure Pop (S: in out Stack; I: in out Item); > package Generic_Stack is > -- exports the procedures imported > procedure Push (S: in out Stack; I: in out Item); > procedure Pop (S: in out Stack; I: in out Item); > end Generic_Stack; Eiffel does this with inheritance. "STACK [T]" would be a deferred class with T as the type of the contents. "push" and "pop" would be routines which are deferred. Descendants of STACK will implement them. You chose between implementations at compile time by deciding which version of stack to create. Everything else just manipulates instances of STACK. >* Multiple implementations, run time -- these are best supported in > Ada by dispatching subprograms and tagged types, not by packaging. Tagged types are the Ada equivalent of Eiffel classes. Paul. -- Paul Johnson | GEC-Marconi Ltd is not responsible for my opinions. | +44 1245 242244 +-----------+-----------------------------------------+ Work: | You are lost in a twisty maze of little Home: | standards, all different.