[Grace-core] Polymorphic/generic classes, etc.

Kim Bruce kim at cs.pomona.edu
Wed Jun 15 23:21:38 PDT 2011


In this e-mail I show some code using matching and then make a proposal for support for parametric polymorphism.

Our Grace implementation is making good progress.  Here is a sample program that compiles (including type-checks) and then runs correctly:

program optionTest{
    interface OptionString {
	 isNone () -> Boolean
	 getOrElse (s:String) -> String
	 }

    object NoneString implements OptionString {
	 method isNone() -> Boolean {true}
	 method getOrElse(default: String) -> String {default}
	 }

    interface SomeStringType {
	 isNone () -> Boolean
	 getOrElse (s:T) -> T
    }

    class SomeString {(x:String) ->
         const value:String := x
         method isNone() -> Boolean {false}
	 method getOrElse(def: String) -> String {value}
	 method get() -> String {value}
	 method ++(s: String) -> String {value ++ s}
    }

    object Tests {
	 method printString(s: OptionString) -> Unit {
	      match (s) {
		    case {str: SomeStringType -> print str.get()}
		    case { (NoneString) -> print "Ignore this line!"}
	       }
	 }
	    
	 var ts: OptionString := SomeString.new("Tim Pawlenty") //boring example string
    }

    Tests.printString(Tests.ts())
    Tests.printString(NoneString)
}

Note that the match statement needed "str: SomeStringType" rather than "str: StringType" because classes can't be used as types.  The version using extractor function (not yet implemented) could replace that with case {SomeString(s) -> ...}" using the class rather than type, a generalization that seems useful.

I have a simple proposal (not yet implemented) for parametric polymorphism that can be illustrated by a variant of the same example.  Type parameters are enclosed in square brackets.

program optionTest{
	interface Option[T] {
	     isNone () -> Boolean
	     getOrElse (s:T) -> T
	     }

	object None[T] implements Option[T] {  // again not sure if this should be an object or class as will be different objects for 
                                                                              // different types
	     method isNone() -> Boolean {true}
	     method getOrElse(default: T) -> T {default}
	}

	interface SomeType[T] {
		  isNone () -> Boolean
		  getOrElse (s:T) -> T
	}

	class Some[T] {(x:T) ->
	      const value:T := x
	      method isNone() -> Boolean {false}
	      method getOrElse(def: T) -> T {value}
	}

	object Tests {
	       method printString(s: Option[String]) -> Unit {
	       	      match (s) {
		      	    case {str: SomeType[String] -> print str.getOrElse("ERROR")}
			    case { (None[String]) -> print "Ignore this line!"}
		      }
		}
		var ts: Option[String] := Some[String].new("Tim Pawlenty") //boring example string
	}

	Tests.printString(Tests.ts())
	Tests.printString(None[String])
}

--------------------------

Hopefully the example is pretty self-explanatory.

We can also support F-bounded polymorphism (and polymorphic methods) as in the following example:

        interface Comparable[T] {
	     compareTo(T) -> Num
        }

        class ComparablePair[T,U] implements Comparable[T]   // builds new comparable out of a simpler one
                          where T extends Comparable[T] {                       // Suggest writing constraint as "where" clause after "implements"
             var key: T
             var kValue: U
             method compareTo(other: ComparablePair[T,U]) -> Num {
                 key.compareTo(other.key)
             }
        }

        class OrderedList[T] implements OrderedListType[T]
                         where T extends Comparable[T] {
             method add(newT: T) -> Unit {
                  var next:T = head
                  ...
                  if (next.compareTo(T) <= 0) then {...}
                  else {...}

             method map[U](f:{(T) -> U}) -> List[U] {...}         // notice how write a polymorphic method
        }

------------------------

While I would have loved to add a MyType construct, I restrained myself (with some difficulty).

Any comments?

Kim





More information about the Grace-core mailing list