Announcement

Collapse
No announcement yet.

PB++ and Class Emulation

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

  • PB++ and Class Emulation

    I've been banging my head against a wall. Somebody forgot to tell me this is a TEAM project. :secret: Thanks for reminding me of that, Rod. And I could also say I've been under the weather for about a week, but I won't say that.

    Anyway, Jim Karabatsos came up with this paradigm for a pre-processor to handle VB classes. I think it's a good one.

    Code:
    Class Foo
        Private _Bar As String
        Private Counter As Long
        Constructor()
            sBar = "INITIALISE ME"
        End Constructor
        Property Let Bar(newValue As String)
            sBar = newValue
            Incr Counter
        End Property
        Property Get Bar() As String
            Property = sBar
        End Property
        Function getUsageCount() As Long
            Function = Counter
        End Function
        Sub resetCounter()
            Counter = 0
        End Sub 
      
    End Class
    
    Dim myFoo As New Foo
    StdOut Foo.Bar
    Foo.Bar = "New Value"
    StdOut Foo.Bar
    StdOut Foo.getUsageCount()
    Foo.Bar = "???"
    StdOut Foo.getUsageCount()
    Foo.resetCounter()
    StdOut Foo.getUsageCount()
    Becomes

    Code:
    Type Foo_VTABLE
        Foo_CLASS_Constructor As DWord
        Foo_CLASS_Property_Let_Bar As DWord
        Foo_CLASS_Property_Get_Bar As DWord
        Foo_CLASS_MethodFunc_getUsageCount As DWord
        Foo_CLASS_MethodSub_resetCounter As DWord
    End Type
    
    Type Foo
         VTABLE As Foo_VTABLE
         sBar As String
         Counter As Long
    End Type
    
    Sub Foo_CLASS_Constructor()
         This.sBar = "INITIALISE ME"
    End Sub
    
    Sub Foo_CLASS_Property_Let_Bar(this As Foo, newValue As String)
         this.sBar = newValue
         Incr Counter
    End Sub
    
    Function Foo_CLASS_Property_Get_Bar(this As Foo) As String
        Function = this.sBar
    End Function
    
    Function Foo_CLASS_MethodFunc_getUsageCount(this As Foo) As Long
         Function = this.Counter
    End Function
    
    Sub Foo_CLASS_MethodSub_resetCounter(this As Foo)
         this.Counter = 0
    End Sub
    
    
    Dim myFoo As Foo : VTABLE_Despatch(Foo, 0)
    
    StdOut VTABLE_Despatch(myFoo, 2) ' Third VTABLE entry Property Get
    Foo.Bar = "New Value"
    VTableDespatch(MyFoo, 1, "New Value") ' do some clever stuff here with optional params
    StdOut VTABLE_Despatch(myFoo, 2) ' Third VTABLE entry Property Get
    StdOut VTABLE_Despatch(myFoo, 3) ' Fourth VTABLE entry function call
    VTableDespatch(MyFoo, 1, "???") ' do some clever stuff here with optional params
    StdOut VTABLE_Despatch(myFoo, 3) ' Fourth VTABLE entry function call
    StdOut VTABLE_Despatch(myFoo, 4) ' Fifth VTABLE entry sub call
    StdOut VTABLE_Despatch(myFoo, 3) ' Fourth VTABLE entry function call
    That's all Jim's code.

    After 6 or 7 bum starts all I've got is this string parser. I think it could end up as a DLL so the GLOBAL array won't interfere with the main thread of vb2pb. Populates a GLOBAL array with each term in the source code line:

    Code:
    #COMPILE EXE      'could be compiled as a DLL that returns pointer to the L
    #DIM ALL
    
    %False = 0
    %True = NOT %False
    
    
    'If the pre-processor is a DLL then this GLOBAL shouldn't interfere in other modules
    GLOBAL arrVBCodeLine() AS STRING * 32     '32 bytes should be big enough for single terms
    
    
    FUNCTION PBMAIN () AS LONG      'all this does is print the results of the parser - no GUI
        LOCAL vbFile AS INTEGER
        LOCAL vbCodeLine AS STRING
        LOCAL Finished AS LONG
        LOCAL i AS LONG
        LOCAL ReportFile AS INTEGER
        LOCAL lElementCount AS LONG
    
        STATIC parrVBCodeLine AS STRING POINTER
    
        DIM arrVBCodeLine(1 TO 1) AS GLOBAL STRING * 32          '32 bytes should be big enough for single terms
    
    
        vbFile = FREEFILE                            'VB source code
        OPEN "frmVBbConvert.frm" FOR INPUT AS vbFile
    
        ReportFile = FREEFILE                        'test report file
        OPEN "ParseTestOutput.txt" FOR APPEND AS ReportFile
    
    
        'test code to make an array report for each line of VB code
        DO
            LINE INPUT #vbFile, vbCodeLine
            IF EOF(vbFile) THEN
                Finished = %True
            ELSE
                Finished = %False
            END IF
    
            PRINT #ReportFile, vbCodeLine
            PRINT #ReportFile, "   *** BECOMES ***"
    
            CALL ParseVBCodeLine(vbCodeLine)
    
            FOR i = 1 TO UBOUND(arrVBCodeLine())
                PRINT #ReportFile, "Element " TRIM$(STR$(i)) " = " arrVBCodeLine(i)
            NEXT i
            PRINT #ReportFile, "------------ END vbCodeLine -----------------"         'delineate each vbCodeLine
            PRINT #ReportFile,
    
        LOOP UNTIL Finished
        PRINT #ReportFile, "============= END OF TEST REPORT ======================"
        CLOSE #vbFile, #ReportFile
    
    END FUNCTION
    
    'THIS is the string parser
    'parse vbCodeLine by spaces into GLOBAL array
    'changes the dimensions of arrVBCodeLine
    SUB ParseVBCodeLine(vbCodeLine AS STRING)
        LOCAL i AS LONG
        LOCAL iCount AS LONG
        LOCAL sCodeLine AS STRING
    
    
        'have to do each individually because they change the size of vbCodeLine
        'treats operators as distinct terms within vbCodeLine
        'double quotes NOT replaced allow easier recognition of string literals
        REPLACE "(" WITH " ( " IN vbCodeLine      'open parentheses
        REPLACE ")" WITH " ) " IN vbCodeLine      'close parentheses
        REPLACE "," WITH " , " IN vbCodeLine      'comma
        REPLACE "." WITH " . " IN vbCodeLine      'period
        REPLACE "&" WITH " & " IN vbCodeLine      'ampersand
        REPLACE "+" WITH " + " IN vbCodeLine      'plus sign
        REPLACE "-" WITH " - " IN vbCodeLine      'minus sign/dash
        REPLACE "*" WITH " * " IN vbCodeLine      'asterisk/multiplication sign
        REPLACE "/" WITH " / " IN vbCodeLine      'slash/division sign
        REPLACE "\" WITH " \ " IN vbCodeLine      'backslash/modulo division sign
        REPLACE "^" WITH " ^ " IN vbCodeLine      'caret/exponent sign
        REPLACE ":" WITH " : " IN vbCodeLine      'colon
        REPLACE ";" WITH " ; " IN vbCodeLine      'semi-colon
        REPLACE "<" WITH " < " IN vbCodeLine      'less than
        REPLACE "=" WITH " = " IN vbCodeLine      'equals
        REPLACE ">" WITH " > " IN vbCodeLine      'greater than
        REPLACE "'" WITH " ' " IN vbCodeLine      'single quote
        REPLACE "  " WITH " " IN vbCodeLine       'eliminate double spaces resulting from above REPLACE list
                                                    'it leaves the original spacing in tact -- meaningful indents
                                                    'and spacing (including line spacing) can be processed
    
        iCount = PARSECOUNT(vbCodeLine, " ")      'count terms delimited by spaces
        REDIM arrVBCodeLine(1 TO iCount)          'resize the array to # of terms - no need to PRESERVE
        PARSE vbCodeLine, arrVBCodeLine(), " "    'put each term in element of array
    
    END SUB
    Do not go quiet into that good night,
    ... Rage, rage against the dark.

  • #2
    Stan,

    After 6 or 7 bum starts all I've got is this string parser. I think it could end up as a DLL so the GLOBAL array won't interfere with the main thread of vb2pb. Populates a GLOBAL array with each term in the source code line:
    I use this technique myself.

    Just as a suggestion, try converting an entire procedure into one string. Doing so makes it simple to locate and identify almost anything. For example, you can determine if a variable scoped to the procedure is actually used or not, or determine if all of the variables in the procedure arguments list are used or not.

    One caveat, do not include quoted literal strings in the parse string as doing so can and usually does have unintended consequences.
    Later...

    JR

    "When governments fear the people there is liberty. When people fear the government there is tyranny." - Thomas Jefferson

    Comment

    Working...
    X