Context: Trait composition has inspired new research in the area of code reuse for object oriented (OO) languages. One of the main advantages of this kind of composition is that it makes possible to separate subtyping from subclassing; which is good for code-reuse, design and reasoning [15]. However, handling of state within traits is difficult, verbose or inelegant.Inquiry: We identify the this-leaking problem as the fundamental limitation that prevents the separation of subtyping from subclassing in conventional OO languages. We explain that the concept of trait composition addresses this problem, by distinguishing code designed for use (as a type) from code designed for reuse (i.e. inherited). We are aware of at least 3 concrete independently designed research languages following this methodology: TraitRecordJ [6], Package Templates [26] and DeepFJig [16].Approach: In this paper, we design 42 µ , a new language, where we improve use and reuse and support the This type and family polymorphism by distinguishing code designed for use from code designed for reuse. In this way 42 µ synthesise the 3 approaches above, and improves them with abstract state operations: a new elegant way to handle state composition in trait based languages.Knowledge and Grounding: Using case studies, we show that 42 µ 's model of traits with abstract state operations is more usable and compact than prior work. We formalise our work and prove that type errors cannot arise from composing well typed code.Importance: This work is the logical core of the programming language 42. This shows that the ideas presented in this paper can be applicable to a full general purpose language. This form of composition is very flexible and could be used in many new languages.
ACM CCS 2012Theory of computation → Formalism; Software and its engineering → Object oriented languages; Designing software; Formal language definitions; 1 IA={interface method int ma()} //interface with abstract method 2 Utils={static method int m(IA a){return ...} } 3 ta={implements IA //This line is the core of the solution 4 method int ma(){return Utils.m(this);}} 5 A=Use taThis code works: Utils relies on interface IA and the trait ta implements IA. Any class reusing ta will contain the code of ta, including the implements IA subtyping declaration; thus any class reusing ta will be a subtype of IA. Therefore, while typechecking Utils.m(this) we can assume this<:IA. It is also possible to add a class B as follows:
12:5Separating Use and Reuse to Improve Both 1 B=Use ta, { method int mb(){return this.ma();} } This also works. B reuses the code of ta, but has no knowledge of A. Since B reuses ta, and ta implements IA, B also implements IA.Later, in appendix A we will provide the type system. Here notice that the former declaration of B is correct even if no method called ma is explicitly declared. DJ and TR would instead require explicitly declaring an abstract ma method: 1 B=Use ta, { method int ma() //not required by us 2 method int mb(){return this.ma();} } In 42 µ , methods are...