Scolring - Forum

Entraides et échanges autour de la technologie Scol - Informations and exchanges on the Scol technology

Vous pouvez changer la langue de l'interface une fois inscrit - You can change the language once registered

You are not logged in.

#1 13-Nov-2015 16:08:10

hebdemnobad
Member
From: northamerica
Registered: 20-Apr-2011
Posts: 1,477
Website

implementing pseudo classes and pseudo inheritance

//this is the pseudo parent of all the classes in this example

struct Animal =[

ihasbackbone:		I, //0 no backbone, 1 backbone
idiet:				I, //0 for vegetarian, 1 for carnivore, 2 for omnivore
ibiome:				I, //0 water, 1 land, 2 air
imulticellular:	I,//0 unicellular, 1 colonial like dcoral, 2 multicellular
igender:				I,//0 hermaphrodite, 1 female, 2 male
ilegs:				I, //0 for none, interger for amount of legs
sname:				S //every animal has a name!
	
	
	]mkAnimal;;
	
//pseudo subclass of Animal	
struct Invertebrate= [
	pclassanimal:		Animal,//parent type of Invertebrate which inherits all properties and functions
	ishelltype:			I //0 no shell, 1 outer shell, 2 vestigial inner shell like a squid
	]mkInvertebrate;;
//pseudo subclass of Invertebrate		
struct Mollusc =[
	pclassInvertebrate:	Invertebrate,
	imollusctype:			I //0 for relatively stationary like clam or mussel, 1 for octopid like octopus, squid, or nautilous
	]mkMollusc;;	
	
	
//create an interface that can accept different objects and process them differently, each object must call a function that returns the constructer that allows the object to be referenced by the interface
	
typedef InterfaceAnimal_Interface = 	
Animal_interface Animal
|
Invertebrate_interface Invertebrate
|
Mollusc_interface Mollusc
|
Other_animal_interface;;

//allow an Animal type object to be a object that implements(?) the InterfaceAnimal_Interface 
fun animal_plug_into_Animal_interface(panimal)=
	Animal_interface panimal;;


fun invertebrate_plug_into_Animal_interface(pInvertebrate)=
	Invertebrate_interface pInvertebrate;;

fun mollusc_plug_into_Animal_interface(pmollusc)=
	Mollusc_interface pmollusc;;

fun invertebrate_dispatcher (pinvertebrate)=
	_fooS "printing an invertebrate fields from  the InterfaceAnimal_Interface";
	_fooS strcat "the name of this invertebrate is " pinvertebrate.pclassanimal.sname;;
	
	
fun printanimalinformation(panimalinterfaceobject)=
	match panimalinterfaceobject with
	(Animal_interface tanimal -> _fooS  "this is an animal or some type of animal")
|
//extract Invertebrate object from  InterfaceAnimal_Interface and send the resulting Invertbrate to a function...I don't see any practical use for this, but it shows you can plug an Invertebrate into the  InterfaceAnimal_Interface and extract an Invertbrate from the  InterfaceAnimal_Interface
	(Invertebrate_interface tInvertebrate -> invertebrate_dispatcher tInvertebrate)
|

	(Mollusc_interface tmollusc -> _fooS "this is an animal and also an invetebrate and also a mollusc or some type of mollusc")
|	
(_ ->  _fooS "this is not an animal, it's a vegetable or mineral");;


// make an animal and set its properties
fun initAnimal(pbackbone, pdiet, pbiome, pmulticellualr, pgender, plegs, pname)=
	
let 	mkAnimal [pbackbone pdiet pbiome pmulticellualr pgender plegs pname]-> lanimal in
(
printanimalinformation (animal_plug_into_Animal_interface lanimal);
lanimal;
);;

// make an Invertebrate and set its properties
fun initInvertebrate(panimal, pshelltype)=
	let mkInvertebrate [panimal pshelltype]-> linvertebrate in
	(
		printanimalinformation (invertebrate_plug_into_Animal_interface linvertebrate);
		linvertebrate;
		
	);; 

	
	
// make an Mollusc and set its properties
fun initMollusc(pinvertebrate, pmollusctype)=
	let mkMollusc [pinvertebrate pmollusctype]-> lmollusc in
	
	(
	printanimalinformation (mollusc_plug_into_Animal_interface lmollusc);
	lmollusc;
	);;

//make a new  mollusc, we know its name, its type of environment, what it eats, how many legs it has, and its mollusc subtype
//some of the arguments will help construct parent objects, and one of them (mollusc subtype) will determine what kind of mollusc it is
//mollusc name, mollusc biome, mollusc diet, mollusc leg amount, invertebrate parent, mollusc subtype
//this function displays the mollusc's properties, including properties of its parent types, and returns a mollusc type since that's the last statement in the function
//i put p in front of each argument, to stand for "pass" as in passing a variable to the function i put l in front of the objects create, since they are local objects, or temporary objects, so i guess after executing the function all that you are left with is its return value, which can be used in other functions, and i guess if it isn't used in other functions, the return value is destroyed after the function is execute too(?)
fun new_mollusc (pname, pbiome, pdiet, plegs, pinvertebrate, pmollusctype)= 
_fooS "\n";
//initAnimal backbone type, diet type, biome type, multiceullartype, gender, amount of legs, and name
	let initAnimal 0 pdiet pbiome  2 0 plegs pname -> lanimal in
//initInvertebrate animal parent class, shell type
	let initInvertebrate lanimal 1 -> linvertebrate in
//initMollusc, invertebrate parent class, mollusc subtype
	let initMollusc linvertebrate pmollusctype -> lmollusc in
	(
	_fooS "making a mollusc";
	_fooS strcat "the mollusc's name is " lmollusc.pclassInvertebrate.pclassanimal.sname;
	_fooS strcat "the mollusc's amount of legs is " (itoa lmollusc.pclassInvertebrate.pclassanimal.ilegs);
	
	
	if (lmollusc.pclassInvertebrate.pclassanimal.idiet == 0) then
	(
	_fooS "this mollusc is a vegetarian";
	)
	else if (lmollusc.pclassInvertebrate.pclassanimal.idiet == 1) then
	(
	_fooS "this mollusc is a carnivore";
	)
	else
	(
	_fooS "since this mollusc doesn't eat just plants or just animals, but has to eat something, because that's what animals do, it's an omnivore.";
	);

	
	
	if (lmollusc.imollusctype == 0) then
	(
	_fooS  "the mollusc doesn't swim alot";
	)
	else
	(
	_fooS  "the mollusc swims all over";
	);


	if (lmollusc.pclassInvertebrate.pclassanimal.ibiome == 0) then
	(
		_fooS "this mollusc lives in the water";
	)
	else
	(
		_fooS "this mollusc lives on land, or maybe is a new type of mollusc that flies through the air!";
	);
	
	lmollusc;
	);;
	
	



	
	fun main()=
		_showconsole; 
		//make a new  mollusc, like a clam or mussel, we know its name, its type of environment, what it eats, how many legs it has, and its mollusc subtype
		//mollusc name, mollusc biome, mollusc diet, mollusc leg amount, invertebrate parent, mollusc subtype
		new_mollusc "clam" 0 2 0 nil 0;
		//this verifies that the function new_mollusc in fact returns a mollusc that we can use
		let new_mollusc "nautilus" 0 1 50 nil 1 -> testmollusc in
		_fooS  strcatn "testing new mollusc function return value"::"this is a mollusc because it has the property named imollusctype and the value of the imollusctype is ":: (itoa testmollusc.imollusctype)::nil;;

when I have time, i'll add a typedef to this, and add some function that would "plug in" and object to a typedef tree (a tree that only splits into branches once, I would think)...I've been reading a book on vb.net, which supports classes, inheritance,  and polymorphism, so I think I understand that typedef is a bit like an Interface in vb.net although I'm sure that there are differences.

while structs are used all the time, I'm finding it hard to figure out where typedef would be useful in a practical application....maybe a simulation or game where different types have to interact in some way (like big monster versus small robot? or small trilobite versus out of control dump truck?)

I can see from my search through the scol voyager folder on my computer that the term isn't used even once in all of the Partition_LockedApp folder's .pkg files.
[edit]

I added a typedef  type named "InterfaceAnimal_Interface" and statements to "plug" each type of animal (animal/invertebrate/mollusk) into the typedef type so a function can be passed various forms of animals and do various things. but I'm still wondering how this can be put to use in games/simulations.

I added a couple of lines at the end of the main function to test that new_mollusc returns a mollusk by referring to one of the mollusc struct's properties, which is imollusctype, which is unique to the mollusc struct.

Last edited by hebdemnobad (13-Nov-2015 19:34:51)

Offline

#2 13-Nov-2015 21:50:07

iri
Admin. / Scol language & Scol apps developer
From: France
Registered: 22-Feb-2009
Posts: 2,024
Website

Re: implementing pseudo classes and pseudo inheritance

Hello,

struct defines a new type. It contains one or several fields. Each field can be a different type (included from another struct) but it is not changeable.
Thus, struct creates a new type. Just this.
struct can be used to encapsulate some objects in a single "opaque" object.

struct Animal =[

ihasbackbone:		I, //0 no backbone, 1 backbone
idiet:				I, //0 for vegetarian, 1 for carnivore, 2 for omnivore
ibiome:				I, //0 water, 1 land, 2 air
imulticellular:	I,//0 unicellular, 1 colonial like dcoral, 2 multicellular
igender:				I,//0 hermaphrodite, 1 female, 2 male
ilegs:				I, //0 for none, interger for amount of legs
sname:				S //every animal has a name!
	] mkAnimal;;

Each field is a function. By example, ihasbackbone has the type : fun [Animal] I. You are an "opque" object in entry, an integer in output which is an elementary object.
mkAnimal is the constructor. You must construct your type before use it.

typedef is like C-union.
Usually in Scol, these unions allow to several types for one variable. You can see this like an interface. It can be too seen like a switch.

typedef InterfaceAnimal_Interface = 	
Animal_interface Animal
| Invertebrate_interface Invertebrate
| Mollusc_interface Mollusc
| Other_animal_interface;;

Each element is a constructor of the InterfaceAnimal_Interface. It is also a function, its type is : fun [Invertebrate] InterfaceAnimal_Interface.
Other_animal_interface can be considered like a "default constructor".
Maybe this can help you to see some usages :
struct => from an "opaque object" to an "elementary object"
typedef => from an "elementary object" to an "opaque object".
However, in these two cases, the "opaque objects" are really different from each other. It is NOT a "reverse" !

typedef is really useful in a pseudo-object programming. If the syntaxe is relatively onerous, it is lighter in memory !.
Otherwise, several typeof replace a typedef, sometimes a struct.

Scol is polymorphic. By example :

fun compareObject (object1, object2)=
  object1 == object2;;

It accepts any type in entry (except S).

More in our wiki :
http://redmine.scolring.org/projects/tu … es_in_Scol

Your code is correct.

Offline

Board footer

Powered by FluxBB