Udemy formation about OOP with PB

Developed or developing a new product in PureBasic? Tell the world about it.
User avatar
microdevweb
Enthusiast
Enthusiast
Posts: 179
Joined: Fri Jun 13, 2014 9:38 am
Location: Belgique

Udemy formation about OOP with PB

Post by microdevweb »

Hey guys,

I created a formation on udemy platform about oop concepts and Pb (sorry but this formation is in french language)

i put some free tickets for you here

https://www.udemy.com/purebasic-program ... de=MCW_POO

For example i teach you how create a database table, this example is using multi heritage class and also abstract methods

Image

needed code for this example without class code (labels are multilingual)

Code: Select all

; **************************************************************************************************
; AUTHEUR : BIELEN PIERRE
; PROJECT : TAB
; MODULE  : TESTE_01.pbi
; **************************************************************************************************
Define flags = #PB_Window_SystemMenu|#PB_Window_ScreenCentered|#PB_Window_SizeGadget
Global.OBJ::DB_TAB myTab
Global.OBJ::DB_TAB_CL_TEXT clName,clSurname
#DB_NAME = "dbTest.db"
Procedure exit()
  End
EndProcedure

Procedure createDbTest()
  If FileSize(#DB_NAME) = -1
    Protected db.OBJ::SQL
    db = SQL::new(#DB_NAME)
    ; création de la table person"
    db\update("CREATE TABLE IF NOT EXISTS 'person' ("+
              "id INTEGER PRIMARY KEY AUTOINCREMENT,"+
              "name TEXT,"+
              "surname TEXT)")
    Protected req.s = "INSERT INTO person (name,surname) VALUES (?,?)"
    Protected i
    For i = 1 To 101
      db\setString(0,"name_"+Str(i))
      db\setString(1,"surname_1"+Str(i))
      db\update(req)
    Next
    db\close()
    
  EndIf
EndProcedure

Procedure resize()
  ResizeGadget(0,0,0,WindowWidth(0),WindowHeight(0))
EndProcedure

createDbTest()

OpenWindow(0,0,0,800,600,"TESTE_01",flags)
ContainerGadget(0,0,0,800,600,#PB_Container_Raised)
BindEvent(#PB_Event_CloseWindow,@exit())
BindEvent(#PB_Event_SizeWindow,@resize())

myTab = DB_TAB::new(#DB_NAME,"person")
myTab\setTitle(LB::new("Person list"+Chr(10)+"Liste des personnes"))
clName = myTab\addColumn(DB_TAB_CL_TEXT::new(LB::new("name"+Chr(10)+"prénom"),"name",0.5))
clSurname = myTab\addColumn(DB_TAB_CL_TEXT::new(LB::new("surname"+Chr(10)+"nom"),"surname",0.5))
clName\setSortEnable(#True)
clSurname\setSortEnable(#True)

myTab\build(0)

Repeat : WaitWindowEvent() : ForEver
Use Pb 5.73 lst and Windows 10

my mother-language isn't english, in advance excuse my mistakes.
User avatar
SparrowhawkMMU
User
User
Posts: 44
Joined: Fri Jan 17, 2014 8:55 pm
Location: UK

Re: Udemy formation about OOP with PB

Post by SparrowhawkMMU »

C'est très généreux, merci :)
User avatar
StarBootics
Addict
Addict
Posts: 984
Joined: Sun Jul 07, 2013 11:35 am
Location: Canada

Re: Udemy formation about OOP with PB

Post by StarBootics »

Hello microdevweb,

I have watch the course you are offering for free and I think you forget something. You are Allocating Structure but you don't freeing it somewhere, and this will probably lead to a memory leak. That being said I like your Character example and now I'm considering to create a program similar to Dev-Module and generate a code similar to this :

Code: Select all

; <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
; Project name : Module OOP
; File Name : Module OOP.pb
; File version: 1.0.0
; Programming : OK
; Programmed by : StarBootics
; Date : 06-04-2019
; Last Update : 06-04-2019
; PureBasic code : V5.70 LTS
; Platform : Windows, Linux, MacOS X
; <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<

DeclareModule Characters
  
  Interface Characters
    GetLife.l()
    GetHealth.l()
    GetName.s()
    SetLife(Life.l)
    SetHealth(Health.l)
    SetName(Name.s)
  EndInterface
  
  Declare.i New(Life.l, Health.l, Name.s)
  Declare Delete(*This)
  
EndDeclareModule

Module Characters
  
  Structure Private_Members
    
    VirtualTable.i
    Life.l
    Health.l
    Name.s
    
  EndStructure
  
  Procedure.l GetLife(*This.Private_Members)
    
    ProcedureReturn *This\Life
  EndProcedure
  
  Procedure.l GetHealth(*This.Private_Members)
    
    ProcedureReturn *This\Health
  EndProcedure
  
  Procedure.s GetName(*This.Private_Members)
    
    ProcedureReturn *This\Name
  EndProcedure
  
  Procedure SetLife(*This.Private_Members, Life.l)
    
    *This\Life = Life

  EndProcedure
  
  Procedure SetHealth(*This.Private_Members, Health.l)
    
    *This\Health = Health
    
  EndProcedure
  
  Procedure SetName(*This.Private_Members, Name.s)
    
    *This\Name = Name
    
  EndProcedure
 
  Procedure New(Life.l, Health.l, Name.s)
    
    *This.Private_Members = AllocateStructure(Private_Members)
    *This\VirtualTable = ?S_METHODS
    SetLife(*This, Life)
    SetHealth(*This, Health)
    SetName(*This, Name)
    
    ProcedureReturn *This
  EndProcedure
  
  Procedure Delete(*This)
    
    If *This <> #Null
      ClearStructure(*This, Private_Members)
      FreeStructure(*This)
    EndIf

  EndProcedure

  DataSection 
    S_METHODS:
    Data.i @GetLife()
    Data.i @GetHealth()
    Data.i @GetName()
    Data.i @SetLife()
    Data.i @SetHealth()
    Data.i @SetName()
    E_METHODS:
  EndDataSection 
  
EndModule

CompilerIf #PB_Compiler_IsMainFile
  
  NewList Characters.Characters::Characters()
  
  AddElement(Characters())
  Characters() = Characters::New(10, 100, "Peter")
  
  Debug "Character Life : " + Str(Characters()\GetLife())
  Debug "Character Health : " + Str(Characters()\GetHealth())
  Debug "Character Name : " + Characters()\GetName()
  
  AddElement(Characters())
  Characters() = Characters::New(11, 95, "Jack")
  
  Debug "-------------------------------------"
  Debug "Character Life : " + Str(Characters()\GetLife())
  Debug "Character Health : " + Str(Characters()\GetHealth())
  Debug "Character Name : " + Characters()\GetName()
  
  Characters()\SetName("StarBootics")
  Characters()\SetLife(12)
  Characters()\SetHealth(100)
  
  Debug "-------------------------------------"
  Debug "Character Life : " + Str(Characters()\GetLife())
  Debug "Character Health : " + Str(Characters()\GetHealth())
  Debug "Character Name : " + Characters()\GetName()
  
  Characters::Delete(Characters())
  DeleteElement(Characters())
  
  Debug "-------------------------------------"
  
  ForEach Characters()
    Debug "Character Life : " + Str(Characters()\GetLife())
    Debug "Character Health : " + Str(Characters()\GetHealth())
    Debug "Character Name : " + Characters()\GetName()
  Next
  
CompilerEndIf

; <<<<<<<<<<<<<<<<<<<<<<<
; <<<<< END OF FILE <<<<<
; <<<<<<<<<<<<<<<<<<<<<<<
Best regards
StarBootics
The Stone Age did not end due to a shortage of stones !
User avatar
Josh
Addict
Addict
Posts: 1183
Joined: Sat Feb 13, 2010 3:45 pm

Re: Udemy formation about OOP with PB

Post by Josh »

@StarBootics

You're absolutely right. The destructor is of course one of the central elements of an object. This is one of the main reasons why I use my simple self-knitted OOP system. The destructor of course does some more things, such as:
  • Close opened windows
  • Free allocated memory
  • Close opend files
  • ...
  • Remove itself or
  • Close the app (only main-object)
In my case, I go one step further:
  • The destructor is a method of the object
  • When creating an object, a parent object is specified in the procedure parameters.
    Only the main object 'App' has no parent object.
  • When the object is created, it enters itself in a list with a reference to the parent object.
  • When I call the destructor of any object, the following happens:
    • The first thing the destructor does is search the list for child objects.
    • If there are child objects, the destructor of the child object is called.
    • The destructor of the child object of course does the same and searches
      first whether it has child objects itself.
So recursively all objects are released and there is no danger to forget anything.
sorry for my bad english
User avatar
microdevweb
Enthusiast
Enthusiast
Posts: 179
Joined: Fri Jun 13, 2014 9:38 am
Location: Belgique

Re: Udemy formation about OOP with PB

Post by microdevweb »

@StarBootics,

don't worry i explain section 26 how destruct the instance of objet. For dot it i don't use directly FreeStructure but i call a method for destruct all linked objects.

example with the class form

Code: Select all

Procedure free(*this._struct)
    With *this
      ForEach \myContent()
        \myContent()\free()
        \title\free()
      Next
      ForEach \myCallBack()
        \myCallBack()\free()
      Next
      FreeStructure(*this)
    EndWith
  EndProcedure
other example my class sql when we close database we free also this object instance
Use Pb 5.73 lst and Windows 10

my mother-language isn't english, in advance excuse my mistakes.
User avatar
mk-soft
Always Here
Always Here
Posts: 5334
Joined: Fri May 12, 2006 6:51 pm
Location: Germany

Re: Udemy formation about OOP with PB

Post by mk-soft »

Each class should include the method Release and perhaps AddRef to protect the object when used multiple times.
So, like the interface "IUnknown"

My internal functions Initialize and Dispose are also called in the correct order when inherited.
In these functions the necessary functions are called to create or release additional memory.
My Projects ThreadToGUI / OOP-BaseClass / EventDesigner V3
PB v3.30 / v5.75 - OS Mac Mini OSX 10.xx - VM Window Pro / Linux Ubuntu
Downloads on my Webspace / OneDrive
Mistrel
Addict
Addict
Posts: 3415
Joined: Sat Jun 30, 2007 8:04 pm

Re: Udemy formation about OOP with PB

Post by Mistrel »

As useful as OOP in PureBasic may at first appear, it is a complete dead-end. One very glaring point is that the language doesn't support even basic call chains for methods.

For example:

Code: Select all

Interface BoxObject
EndInterface

Structure SomeObject
  getBox.BoxObject
EndStructure

*obj.SomeObject=0

; [Error] Garbage at the end of the line.
Debug *obj\getBox() ; <- Can't do it
For a much more lengthy explanation:

viewtopic.php?f=13&t=71028

Even as an introduction to OOP, PureBasic very quickly runs into major problems with traditional paradigms necessary for encapsulation as basic as scope. I've submitted a number of feature requests on how these issues can be addressed but I don't know if they will ever make it into the language.

I would recommend taking a look at Lua as a platform for teaching OOP in education. As unlikely as it may seem, this shockingly spartan language can scale from the embarrassingly procedural all the way to fully-featured OOP with classes and inheritance.
Post Reply