OOP Syntax

For everything that's not in any way related to PureBasic. General chat etc...
Dare
Addict
Addict
Posts: 1965
Joined: Mon May 29, 2006 1:01 am
Location: Outback

OOP Syntax

Post by Dare »

This is a continuation of the OOP discussions, for those who wish to do so.

If people seriously want an OOP implementation of PureBasic, it can probably be done in the first instance as a pre-processor or translator of some sort. That being the case, defining the syntax is probably an important step.

So, what sort of syntax would suit? Our project (if there was one) would translate back to Pure, so it does not need to use Pure interface type syntax. Also the PreProcessor could do more than one pass. Etc Etc. In other words, bias towards Pure but don't be limited by the way it would be done if coding in Pure.

Obviously all PureBasic command/statement syntax remains intact. But for the OOPish stuff?

Eg:

Code: Select all

Class MyThing
  property NameA.l
  property NameB.l
  Method procName.l(par1.l,par2.l)
EndClass

Class myOtherThing
  inherit myThing
  property NameC.l
EndClass

Function procName(par1.l,par2.l)               ; To differentiate from proc
  THIS.NameA + par2
  procName = THIS.NameB + (par2 / par1)
EndFunction

Procedure helloThere(varA.l)                    ; Normal proc but uses wotsit
  ProcedureReturn varA + wotsit.NameA
EndProcedure

Create myWotsit.myThing
myWotsit.NameB = 99
debug myWotsit.procName(11,12)
Excuse the above, it is just to get things going. Priming the pump, so to speak.

Edit: There is also this post: http://www.purebasic.fr/english/viewtopic.php?t=22081
Dare2 cut down to size
User avatar
fsw
Addict
Addict
Posts: 1603
Joined: Tue Apr 29, 2003 9:18 pm
Location: North by Northwest

Post by fsw »

As you can see in the link you posted above I kept the syntax pretty close to pb.

Here again (from the link) what kind of syntax is working now (with my little class parser):

Code: Select all


;oop example by fsw

;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
;- start main:

Class YourObject
  YourValueOfThat.l
  YourAnotherValue.s
  YourThis(par.l)
  YourThat()
EndClass

Class MyObject Extends YourObject
  ValueOfThat.l
  AnotherValue.s
  myThis(par.l)
  myThat()
EndClass

NewObject YourThing.YourObject
NewObject myThing.MyObject
NewObject AnotherThing.MyObject

With myThing
  \myThis(347)
  \myThat()
EndWith

With AnotherThing
  \myThis(123)
  \myThat()
EndWith

With YourThing
  \YourThis(789)
  \YourThat()
EndWith

myThing\YourThis(5)
AnotherThing\YourThis(6)

myThing\YourThat()
AnotherThing\YourThat()
YourThing\YourThat()

End


;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
; for now no constructor or destructor

Procedure YOUROBJECT::yourThis(par.l)
  *THIS\YourValueOfThat = par
EndProcedure

Procedure YOUROBJECT::yourThat()
  *THIS\YourAnotherValue = " That: "
  MessageRequester("YourObject", *THIS\YourAnotherValue + Str(*THIS\YourValueOfThat))
EndProcedure


Procedure MyObject::myThis(par.l)
  *THIS\ValueOfThat = par
EndProcedure

Procedure MyObject::myThat()
  *THIS\AnotherValue = " That: "
  MessageRequester("MyObject", *THIS\AnotherValue + Str(*THIS\ValueOfThat))
EndProcedure
As you can see the only new keywords are:
Class
EndClass
NewObject

All other syntax is normal PB-V4 syntax.


Inheritance is done with:
Extends

The new object is declared with:
NewObject YourObjectName.ClassOfYourObject

The new object is always global, but I'm considering (for compatibily sake) to change the syntax to:
Global NewObject YourObjectName.ClassOfYourObject


The procedure for a class needs the class name in front with a following underscore:
MyClass_ProcName(...

This way procedures in different classes can have the same name.
And you know from the procedurename to which class it belongs to.


The first parameter for a class procedure needs THIS (or SELF or whatever you choose) with the class as the type:
MyClass_ProcName(*this.MyClass, ...


So nothing really new.

Keep it simple :wink:

EDIT:
THIS is now a keyword too.
Double colon is used now for Methods.

Code above changed to reflect the changes.
Last edited by fsw on Thu Jun 01, 2006 6:02 pm, edited 1 time in total.
Kale
PureBasic Expert
PureBasic Expert
Posts: 3000
Joined: Fri Apr 25, 2003 6:03 pm
Location: Lincoln, UK
Contact:

Post by Kale »

Something like this?:

Code: Select all

Class MY_CLASS()
	Protected Name.s
	Protected Address.s
	
	Procedure SetName(Text.s)
		Name.s = Text.s
	EndProcedure
	
	Procedure GetName.s()
		ProcedureReturn Name.s
	EndProcedure

	Procedure SetAddress(Text.s)
		Address.s = Text.s
	EndProcedure
	
	Procedure GetAddress.s()
		ProcedureReturn Address.s
	EndProcedure
	
	Procedure Display.s()
		ProcedureReturn GetName() + " : " + GetAddress()
	EndProcedure
	
	Procedure Constructor()
		Name.s = ""
		Address.s = ""
	EndProcedure
	
	Procedure ~Deconstructor()
		;Whatever
	EndProcedure
EndClass

Class MY_SUBCLASS() Extends MY_CLASS

	Protected TelephoneNumber.s
	
	Procedure SetTelephoneNumber(Text.s)
		TelephoneNumber.s = Text.s
	EndProcedure
	
	Procedure GetTelephoneNumber.s()
		ProcedureReturn TelephoneNumber.s
	EndProcedure

	Procedure Display.s()
		ProcedureReturn GetName() + " : " + GetAddress() + " : " + GetTelephoneNumber()
	EndProcedure
EndClass

NewObject Details.MY_SUBCLASS

Details\SetName("Charlotte the Harlott")
Details\SetAddress("22 Acacia Avenue")
Details\SetTelephoneNumber("666")
Debug Display()
If Purebasic ever moves to support OOP it must be done wholeheartedly. I'm not quite sure how it would be done though.

BUT, you do realise all of this can be done using interfaces??? :wink:
--Kale

Image
thefool
Always Here
Always Here
Posts: 5875
Joined: Sat Aug 30, 2003 5:58 pm
Location: Denmark

Post by thefool »

BUT, you do realise all of this can be done using interfaces???
Don't you read what we write at all? We KNOW its possible, but its practically unreadable!
Kale
PureBasic Expert
PureBasic Expert
Posts: 3000
Joined: Fri Apr 25, 2003 6:03 pm
Location: Lincoln, UK
Contact:

Post by Kale »

thefool wrote:We KNOW its possible, but its practically unreadable!
What a load of rubbish. Interfaces are not that complicated. Why don't you try and see! Once the inital creation is out the way using them is childs play, and you'll probab;y never need to tweak the definition again.
--Kale

Image
inc.
Enthusiast
Enthusiast
Posts: 406
Joined: Thu May 06, 2004 4:28 pm
Location: Cologne/GER

Post by inc. »

Do you like a nice pre-parser Plugin?
http://www.purebasic.fr/german/viewtopi ... hlight=oop
(The Plugin download contains examples and an install how-to)

Its still using the EBP approach but Edel is working on switching the resulted code to the via-interface way without EBP usage like shown in here:
http://www.purebasic-lounge.de/viewtopi ... hlight=oop

Theres a version of jaPBe out where you can set individual new commands for highlightning/folding (identation?).

The syntax of Edels Plugin is very comfortable and C++ like when defining Methods and I already used it in some of my workouts/projects.
Last edited by inc. on Thu Jun 01, 2006 12:10 pm, edited 1 time in total.
Check out OOP support for PB here!
thefool
Always Here
Always Here
Posts: 5875
Joined: Sat Aug 30, 2003 5:58 pm
Location: Denmark

Post by thefool »

Kale wrote:
thefool wrote:We KNOW its possible, but its practically unreadable!
What a load of rubbish. Interfaces are not that complicated. Why don't you try and see! Once the inital creation is out the way using them is childs play, and you'll probab;y never need to tweak the definition again.
Whatever you say; it would be a lot easier with purebasic if it had classes and so on.
User avatar
fsw
Addict
Addict
Posts: 1603
Joined: Tue Apr 29, 2003 9:18 pm
Location: North by Northwest

Post by fsw »

inc. wrote:Do you like a nice pre-parser Plugin?
http://www.purebasic.fr/german/viewtopi ... hlight=oop
(The Plugin download contains examples and an install how-to)

Its still using the EBP approach but Edel is working on switching the resulted code to the via-interface way without EBP usage like shown in here:
http://www.purebasic-lounge.de/viewtopi ... hlight=oop

Theres a version of jaPBe out where you can set individual new commands for highlightning/folding (identation?).

The syntax of Edels Plugin is very comfortable and C++ like when defining Methods and I already used it in some of my workouts/projects.
ENABLEOOP and DISABLEOOP are not C++ keywords.

The double colon is nice (have to look into it...)

AFAIK it's closed source... sorry, but this disqualifies it for me :wink:
User avatar
fsw
Addict
Addict
Posts: 1603
Joined: Tue Apr 29, 2003 9:18 pm
Location: North by Northwest

Post by fsw »

fsw wrote: The double colon is nice (have to look into it...)
Done :!:

Now It's possible to code Methods with:

Code: Select all


Procedure YourObject::SetIt(par.l) ;this is a comment
  *THIS\YourValueOfThat = par
EndProcedure

Procedure YourObject::That()
  *THIS\YourAnotherValue = " That: "
  MessageRequester("YourObject", *THIS\YourAnotherValue + Str(*THIS\YourValueOfThat))
EndProcedure

"THIS" is now a keyword too.
theNerd
Enthusiast
Enthusiast
Posts: 131
Joined: Sun Mar 20, 2005 11:43 pm

Post by theNerd »

This is a very good start!! Using this technique we may be able to have simply OO in PureBasic while retaining all the speed and tightness of code we've grown to expect from it.

Good work!
inc.
Enthusiast
Enthusiast
Posts: 406
Joined: Thu May 06, 2004 4:28 pm
Location: Cologne/GER

Post by inc. »

ENABLEOOP and DISABLEOOP are not C++ keywords.
Jupp for shure not but as nomen-est-omen they do really make sense as its a parser these do got their function in ... guess what ;)
AFAIK it's closed source... sorry, but this disqualifies it for me
Best would getting in contact with edel and Hellhound, sharing ideas concepts how making it easy etc etc etc .... the community will benefit from that :) As I do see you and edel are using almost the same syntax. Hellhounds method results in a very tight sized code-output and offers nice common OOP capabilities.

Cause ..... I do assume that in the future some people will do use that OOP way a lot and when sharing source code in the PB communities it could be a mess if many OOP parsers are out using diff. syntaxes ...
The double colon is nice (have to look into it...)
Thats one of the points I meant, thank you :)

So it would be "theoretically" a perfect thing if the OOP Parser developers like you and edel get in contact and define together a "syntax-OOP-in-PB standard" as he also right now is getting rid of the EBP approach and updating his Plugin refering to Hellhounds approach.

What do you think. Could be more than nice to read interesting sources in threads based on PB OOP where you just have to use "the" PB OOP Plugin for getting it work :)

just my two cents.


PS: I know its said that PB is basic and never well be officially a native OOP supporting language, but hey .... if some people like it and getting together making new stuff for it then lets at least speak the same language as if not the OOP approach will be even more difficult to newbies when they hear "Oh, these OOP believers made it even more complicated as many parsers are out using diff. syntaxes so just start getting into the jungle".
Check out OOP support for PB here!
User avatar
fsw
Addict
Addict
Posts: 1603
Joined: Tue Apr 29, 2003 9:18 pm
Location: North by Northwest

Post by fsw »

Have you looked at my generated code?

This code:

Code: Select all


;oop example by fsw

;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
;- start main:

Class MyObject
  ValueOfThat.l
  AnotherValue.s
  myThis(par.l)
  myThat()
EndClass

Global NewObject myThing.MyObject  ;this is a comment

With myThing
  \myThis(347)
  \myThat()
EndWith

myThing\myThat()

End

;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
; for now no constructor or destructor

Procedure MyObject::myThis(par.l)
  *THIS\ValueOfThat = par
EndProcedure

Procedure MyObject::myThat()
  *THIS\AnotherValue = " That: "
  MessageRequester("MyObject", *THIS\AnotherValue + Str(*THIS\ValueOfThat))
EndProcedure
gets translated to:

Code: Select all

; ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
; Special Notes About This Code:
; 
; This code uses a NewArray Macro
; Dim does look too weird...
; It also goes well with NewList...
;
; Macro NewArray
;   Dim
; EndMacro
;
; Uncomment this macro if you don't
; have it in a res file already...
; ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

;oop example by fsw

;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
;- start main:

; Start of class
Structure MYOBJECT : VTable.l
  ValueOfThat.l
  AnotherValue.s
EndStructure

Interface MYOBJECT_Methods
  myThis(par.l)
  myThat()
EndInterface


Declare MYOBJECT_myThis(*THIS.MYOBJECT, par.l)
Declare MYOBJECT_myThat(*THIS.MYOBJECT)


DataSection : MYOBJECT_VTable:
  Data.l @MYOBJECT_myThis()
  Data.l @MYOBJECT_myThat()
EndDataSection : Global NewArray MYOBJECT_Self.MYOBJECT(0)
; End of class




; Define Object
ReDim MYOBJECT_Self.MYOBJECT(0) : MYOBJECT_Self(0)\VTable = ?MYOBJECT_VTable : Global MYTHING.MYOBJECT_Methods = MYOBJECT_Self(0) ;THIS IS A COMMENT

With myThing
  \myThis(347)
  \myThat()
EndWith

myThing\myThat()

End

;~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
; for now no constructor or destructor

Procedure MYOBJECT_MYTHIS(*THIS.MYOBJECT, PAR.L) ;
  *THIS\ValueOfThat = par
EndProcedure

Procedure MYOBJECT_MYTHAT(*THIS.MYOBJECT) ;
  *THIS\AnotherValue = " That: "
  MessageRequester("MyObject", *THIS\AnotherValue + Str(*THIS\ValueOfThat))
EndProcedure
IMHO it's much shorter and readable as what I've seen so far.

The other techniques use prototypes or/and EBP or Danilo's (PBv3) appoach.

Using DataSections (since PBv4) is much easier, shorter and readable IMHO.
inc.
Enthusiast
Enthusiast
Posts: 406
Joined: Thu May 06, 2004 4:28 pm
Location: Cologne/GER

Post by inc. »

Ok, Datasections do make it easier, but why that NewArray Way?

What about this?

Code: Select all

Structure cMYOBJECT : VTable.l:
    Value.l
    AnotherValue.s
EndStructure

Interface iMYOBJECT
    GetVal(PAR.l)
    ShowVal()
EndInterface

Procedure iMYOBJECT_GetVal(*THIS.cMYOBJECT, PAR.l) ;
    *THIS\Value = PAR
EndProcedure

Procedure iMYOBJECT_ShowVal(*THIS.cMYOBJECT) ;
    *THIS\AnotherValue = "Value: "
    MessageRequester("MyObject", *THIS\AnotherValue + Str(*THIS\Value))
EndProcedure

Procedure.l New_MYOBJECT()
    Protected *obj.cMYOBJECT
    *obj = AllocateMemory(SizeOf(cMYOBJECT))
    *obj\VTable = ?MYOBJECT_VTable
    ProcedureReturn *obj
EndProcedure


DataSection : MYOBJECT_VTable:
    Data.l @iMYOBJECT_GetVal()
    Data.l @iMYOBJECT_ShowVal()
EndDataSection

; Example 1: A single obj

Code: Select all

MYTHING.iMYOBJECT = New_MYOBJECT()
MYTHING\GetVal(347)
MYTHING\ShowVal()

; Example 2: An array of objs

Code: Select all

Dim AnotherThing.iMYOBJECT(5)
For i = 0 To 5
    AnotherThing(i) = New_MYOBJECT()
    AnotherThing(i)\GetVal(i)
    AnotherThing(i)\ShowVal()
Next i
The generation of an array of objs could be easely implemented in your parser so the follwoing would be possible

Code: Select all

NewObject myThing.MyObject(5)

For i = 0 To 5
    myThing(i)\GetVal(i)
    myThing(i)\ShowVal()
Next i
Check out OOP support for PB here!
User avatar
blueznl
PureBasic Expert
PureBasic Expert
Posts: 6166
Joined: Sat May 17, 2003 11:31 am
Contact:

Post by blueznl »

i know NOTHING about oop (perhaps better keep it that way :-)) but i might offer some comments

i would try to stay a bit closer to the nature of basic, as if there is one :-)

i understand there are three catagories, objects, classes, and methods... but euh... i do not understand the difference fully :-) especially the concept of 'classes' :-)

lemme try...

Code: Select all

Class car
  ;
  direction.l
  speed.l
  ;
  Method slower()
    speed = speed-1
  EndMethod
  ;
  Method faster()
    speed = speed-1
  EndMethod
  ;
EndClass
i would prefer the use of a new keyword 'method' over the old 'procedure', just for readability

Code: Select all

corvette.car
corvette\faster()
with perhaps the optional keyword 'Object'

Code: Select all

Object corvette.car
this would pretty much look like a sort of extended structuring, not only could you use primitives, but also build in procedures etc.

from a readability point of view, everything would look pretty much like regular pb this way

not sure if this makes sense, i dunno anything about oop :-)
( PB6.00 LTS Win11 x64 Asrock AB350 Pro4 Ryzen 5 3600 32GB GTX1060 6GB)
( The path to enlightenment and the PureBasic Survival Guide right here... )
inc.
Enthusiast
Enthusiast
Posts: 406
Joined: Thu May 06, 2004 4:28 pm
Location: Cologne/GER

Post by inc. »

Object corvette.car
very above in fsw's way is:
NewObject corvette.car
corvette.car
corvette\faster()
... needs first to be constructed:
corvette.car = New_car() ; Class car
corvette\faster()
or in the parsers syntax ..
NewObject corvette.car
corvette\faster()
i would prefer the use of a new keyword 'method' over the old 'procedure', just for readability
Ok, but infact they are procedures/routines so imho theres no need to do a naming separation ;)

so ...
Procedure ClassName::Methodname(param.l)
*this\Value = param
EndProcedure
.. is been kept in the parser syntax easy imho
Check out OOP support for PB here!
Post Reply