| Register | FAQ | Calendar | Search | Today's Posts | Mark Forums Read |
|
#1
| |||
| |||
| In JAVA language, single inheritance is compensated by another feature : the interface. A JAVA interface enables to declare an abstract type associated to specific routines (only signatures). An object may only extend a single father object (single inheritance) but may also implement as many interfaces as necessary. In some way, the notion of interface replaces templates (but not exactly because templates have also been introduced in the last JAVA version). I think that JAVA interfaces are often more interesting that direct inheritance. Unfortunately, I was unable to find a similar feature in F2003. This could be easily translated into F20xx. I propose here a simple syntax on an actual example : module ordered type, abstract :: ordered_type contains generic :: operator(<=) => lessthan end type contains function lessthan(a,b) RESULT(r) type(ordered_type),intent(in) :: a,b logical :: r end function end module Here the type "ordered_type", declared "abstract", plays the role of a JAVA interface. All procedures binded to that abstract type are only signatures like in FORTRAN interfaces. Any actual type may implement that abstract type : the only condition is to provide the right version of the binded procedures. type,implements (ordered_type) :: mytype ... contains generic :: operator(<=) => mytype_lessthan ... end type Of course, it will be easy to implement several abstract types with the syntax : type,implements(a1,a2 ...) :: mytype contains ... end type It is now possible to write general modules working only on abstract types (like templates). As example, I take again the module "quicksort" described in a previous post but limited to an array of real values. It will apply now on the abstract type "ordered_type" : module quicksort use ordered contains recursive subroutine QsortC(A) type(ordered_type), intent(in out), dimension( :: Ainteger :: iq if(size(A) > 1) then call Partition(A, iq) call QsortC(A(:iq-1)) call QsortC(A(iq )endif end subroutine QsortC subroutine Partition(A, marker) type(ordered_type), intent(in out), dimension( :: Ainteger, intent(out) :: marker integer :: i, j type(ordered_type) :: temp type(ordered_type) :: x ! pivot point x = A(1) i= 0 j= size(A) + 1 do j = j-1 do if (A(j) <= x) exit j = j-1 end do i = i+1 do if (x <= A(j)) exit i = i+1 end do if (i < j) then ! exchange A(i) and A(j) temp = A(i) A(i) = A(j) A(j) = temp elseif (i == j) then marker = i+1 return else marker = i return endif end do end subroutine Partition end module And here is a test program showing the definition of actual types implementing the abstract type : program test use quicksort type, implements(ordered_type) :: t1 real :: value contains generic :: operator(<=) => reallessthan end type type, implements(ordered_type) :: t2 integer :: value contains generic :: operator(<=) => integerlessthan end type integer,parameter :: n=1000 type(t1) :: list1(n) type(t2) :: list2(n) integer :: i call random_number(list1( %value)call random_number(list2( %value)call qsortc(list1) call qsortc(list2) contains function reallessthan(r1,r2) result(r) type(t1) :: r1,r2 logical :: r r=r1%value <= r2%value end function function integerlessthan(i1,i2) result(r) type(t2) :: i1,i2 logical :: r r=i1%value <= i2%value end function end program |
|
#2
| |||
| |||
| fj schrieb: [...] > > type,implements (ordered_type) :: mytype type, extends(ordered_type) :: mytype F2003 does support extension of abstract types, as well as deferred implementations. There are unfortunately only few compilers which implement the standard in this area. Regards |
|
#3
| |||
| |||
| On Aug 25, 12:11 am, Reinhold Bader <Ba...@lrz.de> wrote: > fj schrieb: > [...] > > > > > type,implements (ordered_type) :: mytype > > type, extends(ordered_type) :: mytype > > F2003 does support extension of abstract types, as well > as deferred implementations. There are > unfortunately only few compilers which implement the standard > in this area. > > Regards The IBM compiler supports extension of abstract types and deferred bindings. gfortran is making substantial progress in this arena. I'll bet they'll support these features before too long. Damian |
|
#4
| |||
| |||
| On 25 août, 09:11, Reinhold Bader <Ba...@lrz.de> wrote: > fj schrieb: > [...] > > > > > type,implements (ordered_type) :: mytype > > type, extends(ordered_type) :: mytype > > F2003 does support extension of abstract types, as well > as deferred implementations. There are > unfortunately only few compilers which implement the standard > in this area. > > Regards I don't want to use the inheritance here (because F2003 supports only a single inheritance). For instance, I want to be able to declare something like that : type, extends(roottype), implements(ordered_type) :: mytype In JAVA, on write something like : class mytype extends rootype implements ordered_type { ... } The inheritance is already used (extension of "roottype" which is not an abstract type) and I want to imposed a behavior using an abstract type (ordered_type). Is the following authorized by F2003 ? type, extends(roottype,ordered_type) :: mytype where only one of the types listed in the "extends" field may be a non abstract type ? |
|
#5
| |||
| |||
| fj schrieb: > I don't want to use the inheritance here (because F2003 supports only > a single inheritance). For instance, I want to be able to declare > something like that : > > type, extends(roottype), implements(ordered_type) :: mytype Well, your initial example did not indicate this. In any case, this is a form of limited multiple inheritance which indeed is not supported explicitly. You can however have a type definition type, extends(ordered_type) :: mytype type(roottype) :: r : contains : ! map needed TBPs of roottype, as well as deferred methods of ordered_type end type which will do the equivalent with only a little additional wrapper code. If you need to override roottype methods anyway, the needed programming effort is in fact the same. [...] Regards |
|
#6
| |||
| |||
| On 25 août, 10:21, Reinhold Bader <Ba...@lrz.de> wrote: > fj schrieb: > > > I don't want to use the inheritance here (because F2003 supports only > > a single inheritance). For instance, I want to be able to declare > > something like that : > > > type, extends(roottype), implements(ordered_type) :: mytype > > Well, your initial example did not indicate this. In any case, this is a > form of limited multiple inheritance which indeed is not supported explicitly. > You can however have a type definition > > type, extends(ordered_type) :: mytype > type(roottype) :: r > : > contains > : ! map needed TBPs of roottype, as well as deferred methods of ordered_type > end type > > which will do the equivalent with only a little additional wrapper code. > If you need to override roottype methods anyway, the needed programming effort > is in fact the same. > > [...] > > Regards But this is a pity because extending an abstract type associated with predefined routine signatures is much easier than extending a actual type. And because this is much easier, it is possible in JAVA to extends (more precisely to implement) as many abstract types (JAVA interfaces) as necessary when it is possible to extend only a unique actual type (single inheritance). |
|
#7
| |||
| |||
| On Aug 25, 10:31*am, fj <francois.j...@irsn.fr> wrote: > On 25 août, 10:21, Reinhold Bader <Ba...@lrz.de> wrote: > > > fj schrieb: > > > > I don't want to use the inheritance here (because F2003 supports only > > > a single inheritance). For instance, I want to be able to declare > > > something like that : > > > > * type, extends(roottype), implements(ordered_type) :: mytype > > > Well, your initial example did not indicate this. In any case, this is a > > form of limited multiple inheritance which indeed is not supported explicitly. > > You can however have a type definition > > > type, extends(ordered_type) :: mytype > > * *type(roottype) :: r > > * *: > > contains > > * *: ! map needed TBPs of roottype, as well as deferred methods of ordered_type > > end type > > > which will do the equivalent with only a little additional wrapper code.. > > If you need to override roottype methods anyway, the needed programmingeffort > > is in fact the same. > > > [...] > > > Regards > > But this is a pity because extending an abstract type associated with > predefined routine signatures is much easier than extending a actual > type. > > And because this is much easier, it is possible in JAVA to extends > (more precisely to implement) as many abstract types (JAVA interfaces) > as necessary when it is possible to extend only a unique actual type > (single inheritance). Please explain how this does any real good in Fortran at all. As I understand it, you can not pass an array of integers to a routine which expects an array of elements, each of which is of derived type, each of which consists only of an integer. - e |
|
#8
| |||
| |||
| On Aug 25, 8:17*pm, glen herrmannsfeldt <g...@ugcs.caltech.edu> wrote: > e p chandler wrote: > > (snip) > > > Please explain how this does any real good in Fortran at all. As I > > understand it, you can not pass an array of integers to a routine > > which expects an array of elements, each of which is of derived type, > > each of which consists only of an integer. > > In Java, you can't have arrays of objects, but only > arrays of object reference variables. * The closest you > would get in Fortran would be arrays of pointers. > Oops, no arrays of pointers, arrays of structures > containing pointers. > > Now, can you use a pointer to integer equivalently > to a pointer to a structure containing only an > integer? *Or one with the integer at the beginning? > > -- glen I just want to call wonder_routine(int_array) where int_array is an ordinary array of integers. I don't care what the routine does underneath. I do know that I get a type mismatch error when I pass an array of integers to a routine expecting an array of a derived type. So right now I'm close to serious mirth when what I thought was a relatively straight forward question about Fortran is answered in terms of Java _and_ the properties of pointers in C! :-) - e |
|
#9
| |||
| |||
| e p chandler wrote: (snip) > Please explain how this does any real good in Fortran at all. As I > understand it, you can not pass an array of integers to a routine > which expects an array of elements, each of which is of derived type, > each of which consists only of an integer. In Java, you can't have arrays of objects, but only arrays of object reference variables. The closest you would get in Fortran would be arrays of pointers. Oops, no arrays of pointers, arrays of structures containing pointers. Now, can you use a pointer to integer equivalently to a pointer to a structure containing only an integer? Or one with the integer at the beginning? -- glen |
|
#10
| |||
| |||
| On 26 août, 01:01, e p chandler <e...@juno.com> wrote: > On Aug 25, 10:31 am, fj <francois.j...@irsn.fr> wrote: > > > > > On 25 août, 10:21, Reinhold Bader <Ba...@lrz.de> wrote: > > > > fj schrieb: > > > > > I don't want to use the inheritance here (because F2003 supports only > > > > a single inheritance). For instance, I want to be able to declare > > > > something like that : > > > > > type, extends(roottype), implements(ordered_type) :: mytype > > > > Well, your initial example did not indicate this. In any case, this is a > > > form of limited multiple inheritance which indeed is not supported explicitly. > > > You can however have a type definition > > > > type, extends(ordered_type) :: mytype > > > type(roottype) :: r > > > : > > > contains > > > : ! map needed TBPs of roottype, as well as deferred methods of ordered_type > > > end type > > > > which will do the equivalent with only a little additional wrapper code. > > > If you need to override roottype methods anyway, the needed programming effort > > > is in fact the same. > > > > [...] > > > > Regards > > > But this is a pity because extending an abstract type associated with > > predefined routine signatures is much easier than extending a actual > > type. > > > And because this is much easier, it is possible in JAVA to extends > > (more precisely to implement) as many abstract types (JAVA interfaces) > > as necessary when it is possible to extend only a unique actual type > > (single inheritance). > > Please explain how this does any real good in Fortran at all. As I > understand it, you can not pass an array of integers to a routine > which expects an array of elements, each of which is of derived type, > each of which consists only of an integer. > > - e OK : my example (quicksort) was not the best choice. I agree with you : an array of integers cannot match an array of derived types. This is also true in JAVA as well (but in JAVA one also disposes of the class Integer in parallel to the scalar int). In fact I just wanted to show that extending abstract types could be an interesting feature for FORTRAN. This is not really inheritance because you do not inherit neither data (the abstract type is empty) nor routines (the abstract type is associated to abstract routines : only the signatures are interesting). Let us assume that you have already defined a derived type "t1" extending "rt1" and a derived type "t2" extending "rt2". But t1 and t2 have to follow a same behavior which does not concern neither rt1 nor rt2. Then it becomes possible to create routines receiving as argument an object having just to follow the expected behavior. The behavior in my example was the operator <= : any object providing this operator becomes a valid argument matching the abstract type. This is often the case in scientific modeling : for instance a "air" mesh and a "concrete" mesh have practically no common fields. But one might need to compute the enthalpy and the density for both ... You can say that one just need to extend a common type binded to enthalpy and density routines. Yes but this is not possible today if the "air" mesh already extends a "fluid" mesh and the concrete mesh already extends a "wall" mesh. Of course you could say that one can add in the "fluid" and "wall" mesh routines computing the enthalpy and the density. That's true but you do the job twice which is not very useful if other extended fluid and wall objects to not need to compute enthalpy and density. To define a behavior, one just need to create an abstract type "at" binded to the operator <=. The type "t1" and "t2" have to extend "at" in some way. I proposed the syntax : type,extend(rt1),implements(at) :: rt1 But a syntax like type,extend(rt1,at) :: rt1 could be adopted with the limitation that only one type in the list "extends" could be non abstract. It will even become possible to build up an array of objects matching that abstract type using the F2003 class keyword : class(ab),ALLOCATABLE :: v( ![]() As summary, extending an abstract type allows a kind of simplified multiple inheritance without most of the difficulties associated to general multiple inheritance. |
![]() |
| Thread Tools | |
| Display Modes | |
In an effort to better serve ads to our visitors, cookies are used on objectmix.com. For more information, check out our Privacy Policy.