Results 1 to 10 of 10

Thread: String substitutions with variables in vb6

  1. #1

    Thread Starter
    Addicted Member Davor Geci's Avatar
    Join Date
    Sep 2009
    Posts
    222

    String substitutions with variables in vb6

    Hello do we have in vb6 something more simple to do this:

    Code:
    myNumber = 6
    myProduct = "Table"
    
    myString = "This is my %i try to use this %j in my life"
    
    myString = Replace (myString, "%i", myNumber)
    myString = Replace (myString, "%j", myProduct)
    and now to replace the %i and %j with the values from the variables or is this the only way?

    P.S.
    this is also not the best solution:

    Code:
    myNumber = 6
    myProduct = "Table"
    
    myString = "This is my " & myNumber & " try to use this " & myProduct & " in my life"
    I would like to implement multilanguage in my app so that I have one string for this in my replacement language file
    Last edited by Davor Geci; Aug 14th, 2018 at 10:28 AM.
    My projects:
    Virtual Forms
    VBA Telemetry

  2. #2
    PowerPoster
    Join Date
    Jun 2015
    Posts
    2,224

    Re: String substitutions with variables in vb6

    I use an Expand() function, that basically does {token} substitution, with provided source data.
    The source data is typically a collection, a recordset object or even environment variables.

    But usually this snippet is sufficient.

    Code:
    ''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
    Public Function Fmt$(Format As String, ParamArray Args())
    '   Minimal Sequential {Token#} Replacing ie: {0} {1}
    '   Replaces '\n' With vbNewLine
    '   Replaces '\t' With vbTab
    ''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
        Fmt = Replace(Format, "\n", vbNewLine)
        Fmt = Replace(Fmt, "\t", vbTab)
        Dim Arg As Long
        For Arg = 0 To UBound(Args)
            Fmt = Replace(Fmt, "{" & Arg & "}", Nz(Args(Arg)))
        Next
    End Function
    So
    Code:
    myString = Fmt("This is my {0} try to use this {1} in my life", myNumber, myProduct)
    Last edited by DEXWERX; Aug 14th, 2018 at 11:26 AM. Reason: collection not connection...

  3. #3
    PowerPoster
    Join Date
    Feb 2012
    Location
    West Virginia
    Posts
    14,205

    Re: String substitutions with variables in vb6

    Seems a bit odd, would you not need to replace the entire string if you are doing multiple languages? Seems that replacing just a word here and there would not be of much use.

  4. #4

  5. #5
    PowerPoster
    Join Date
    Jun 2015
    Posts
    2,224

    Re: String substitutions with variables in vb6

    Quote Originally Posted by DataMiser View Post
    Seems a bit odd, would you not need to replace the entire string if you are doing multiple languages? Seems that replacing just a word here and there would not be of much use.
    yes.. the whole string _is_ replaced from a string table resource. The token replacement is only tangentially related to using string resources in general.

    string resources are stored with the embedded tokens.... -_-
    Last edited by DEXWERX; Aug 14th, 2018 at 02:54 PM.

  6. #6
    PowerPoster ChrisE's Avatar
    Join Date
    Jun 2017
    Location
    Frankfurt
    Posts
    3,044

    Re: String substitutions with variables in vb6

    Hi,

    he one more option..

    Code:
    Option Explicit
    
    Private Tb() As String
    
    Private Sub Command1_Click()
          Text2.Text = ConvertText(Text1.Text, Tb())
    End Sub
    
    Private Sub Form_Load()
    
       Dim i As Long
       
          'Tabelle initialisieren
          ReDim Tb(255)
          'Ansi Werte 1:1 zuweisen
          'A=A, a=a etc.
          For i = 0 To UBound(Tb)
             Tb(i) = Chr(i)
          Next
    'Test:
          Tb(Asc("h")) = "Green"
          Tb(Asc("a")) = "(5000)"
          Tb(Asc("b")) = "(5005)"
          Tb(Asc("c")) = "(5010)"
          Tb(Asc("Z")) = "Y"
    
          'Textbox vorbesetzen
          Text1.Text = "habcZ"
          Text2.Text = vbNullString
    End Sub
    
    '------------------------------------------------------------
    'einen Text konvertieren nach einer vorbelegten CodeTabelle
    'die Zeichenlänge in der Codetabelle ist variabel von 1 bis n
    '------------------------------------------------------------
    Public Function ConvertText(sText As String, _
                                CodeTb() As String) As String
    
       Dim i As Long, j As Long, z As Long
       Dim Buffer As String
       
          'Buffer dimensionieren
          Buffer = Space(128)
          'zum Test nur mit 2 Spaces
          Buffer = Space(2)
       
          'in Schleife Text Zeichen für Zeichen abarbeiten
          For i = 1 To Len(sText)
             'Dezimalwert des nächsten Zeichens
             z = Asc(Mid$(sText, i, 1))
             'Buffer überprüfen
             Do
                'passt der umgesetzte Code noch rein
                If (j + Len(CodeTb(z))) <= Len(Buffer) Then
                   'ja, keine Anpassung notwendig
                   Exit Do
                End If
                'Buffer vergrössern um 50%
                Buffer = Buffer & Space(Len(Buffer) / 2)
             Loop
             
             'Zeichen übersetzen & einfügen
             Mid$(Buffer, j + 1) = CodeTb(z)
             'belegte Länge im Buffer aktualisieren
             j = j + Len(CodeTb(z))
          Next
          
          'nur belegten Teil des Buffers als Ergebnis liefern
          ConvertText = Left$(Buffer, j)
    End Function
    regards
    Chris
    to hunt a species to extinction is not logical !
    since 2010 the number of Tigers are rising again in 2016 - 3900 were counted. with Baby Callas it's 3901, my wife and I had 2-3 months the privilege of raising a Baby Tiger.

  7. #7
    PowerPoster wqweto's Avatar
    Join Date
    May 2011
    Location
    Sofia, Bulgaria
    Posts
    5,120

    Re: String substitutions with variables in vb6

    I'm using something similar to DEXWERX's function:
    thinBasic Code:
    1. Public Function Printf(ByVal sText As String, ParamArray A() As Variant) As String
    2.     Const LNG_PRIVATE   As Long = &HE1B6 '-- U+E000 to U+F8FF - Private Use Area (PUA)
    3.     Dim lIdx            As Long
    4.    
    5.     For lIdx = UBound(A) To LBound(A) Step -1
    6.         sText = Replace(sText, "%" & (lIdx - LBound(A) + 1), Replace(A(lIdx), "%", ChrW$(LNG_PRIVATE)))
    7.     Next
    8.     Printf = Replace(sText, ChrW$(LNG_PRIVATE), "%")
    9. End Function
    This would be used like this in your case:

    myString = Printf("This is my %1 try to use this %2 in my life", myNumber, myProduct)

    i.e. %1 is expanded with first arg, %2 with second, etc.

    The function is longer as it takes care when the actual value in myNumber contains %2 *not* to replace this placeholder with myProduct in the second itertion of the replacement loop.

    Anyway, this seems good enough for short strings and if performance is consideration and/or dealing with larger texts then you can investigate regular expressions and string builders to achieve equivalent results with less string allocations.

    cheers,
    </wqw>

  8. #8
    PowerPoster
    Join Date
    Feb 2006
    Posts
    24,482

    Re: String substitutions with variables in vb6

    You could make one pass to determine the expanded length, then another to plop things into an allocated String via Mid$() statements:

    Code:
    Option Explicit
    
    Private Function Expand(ByRef Template As String, ParamArray Args() As Variant) As String
        'Insertions %0 through %9, escape literal % as %%.
        Const ASC0 As Long = &H30& 'AscW("0").
        Dim I As Long
        Dim TemplPos As Long
        Dim Escaped As String
        Dim Expansion As Long
        Dim NewPos As Long
        Dim OutPos As Long
        Dim Text As String
    
        If 0 > UBound(Args) Or UBound(Args) > 9 Then
            Err.Raise 5 'Invalid procedure call or argument.
        End If
        For I = 0 To UBound(Args)
            Args(I) = CStr(Args(I))
        Next
        Do
            TemplPos = InStr(TemplPos + 1, Template, "%")
            If TemplPos > 0 Then
                TemplPos = TemplPos + 1
                Escaped = Mid$(Template, TemplPos, 1)
                If Escaped = "%" Then
                    Expansion = Expansion - 1
                Else
                    If "0" > Escaped Or Escaped > "9" Then
                        Err.Raise 5 'Invalid procedure call or argument.
                    End If
                    Expansion = Expansion + (Len(Args(AscW(Escaped) - ASC0)) - 2)
                End If
            End If
        Loop While TemplPos > 0
        Expand = Space$(Len(Template) + Expansion)
        OutPos = 1
        Do
            NewPos = InStr(TemplPos + 1, Template, "%")
            If NewPos > 0 Then
                Mid$(Expand, OutPos) = Mid$(Template, TemplPos + 1, NewPos - TemplPos - 1)
                OutPos = OutPos + NewPos - TemplPos - 1
                NewPos = NewPos + 1
                Escaped = Mid$(Template, NewPos, 1)
                If Escaped = "%" Then
                    Mid$(Expand, OutPos) = "%"
                    OutPos = OutPos + 1
                Else
                    Text = Args(AscW(Escaped) - ASC0)
                    Mid$(Expand, OutPos) = Text
                    OutPos = OutPos + Len(Text)
                End If
            Else
                Mid$(Expand, OutPos) = Mid$(Template, TemplPos + 1)
            End If
            TemplPos = NewPos
        Loop While TemplPos > 0
    End Function
    
    Private Sub Form_Load()
        AutoRedraw = True
        Print "Hi %0."
        Print "["; Expand("Hi %0.", "Joe"); "]"
        Print
        Print "Please send $%2 to %0 %1.  %0 needs it now."
        Print "["; _
              Expand("Please send $%2 to %0 %1.  %0 needs it now.", _
                     "Joe", _
                     "Veeblefester", _
                     150@); _
              "]"
        Print
        Print "Only %0%% per month, act now!"
        Print "["; Expand("Only %0%% per month, act now!", 2.35); "]"
    End Sub

  9. #9

    Thread Starter
    Addicted Member Davor Geci's Avatar
    Join Date
    Sep 2009
    Posts
    222

    Re: String substitutions with variables in vb6

    Yes, guys this is just the thing that I wanted.

    Thanks to all of you. I will test your solutions and see how this impact to the speed also.

    Davor
    My projects:
    Virtual Forms
    VBA Telemetry

  10. #10
    PowerPoster wqweto's Avatar
    Join Date
    May 2011
    Location
    Sofia, Bulgaria
    Posts
    5,120

    Re: String substitutions with variables in vb6

    thinBasic Code:
    1. Public Function PrintfEx(ByVal sText As String, ParamArray A() As Variant) As String
    2.     Static oRegExp      As Object
    3.     Dim lSize           As Long
    4.     Dim lIdx            As Long
    5.     Dim lPrevIndex      As Long
    6.     Dim lPos            As Long
    7.     Dim sValue          As String
    8.    
    9.     If oRegExp Is Nothing Then
    10.         Set oRegExp = CreateObject("VBScript.RegExp")
    11.         oRegExp.Global = True
    12.         oRegExp.Pattern = "%\d+"
    13.     End If
    14.     lSize = Len(sText)
    15.     With oRegExp.Execute(sText)
    16.         For lIdx = 0 To .Count - 1
    17.             With .Item(lIdx)
    18.                 sValue = A(Mid$(.Value, 2) - 1)
    19.                 lSize = lSize - .Length + Len(sValue)
    20.             End With
    21.         Next
    22.         PrintfEx = String$(lSize, 0)
    23.         lPos = 1
    24.         For lIdx = 0 To .Count - 1
    25.             With .Item(lIdx)
    26.                 lSize = .FirstIndex - lPrevIndex
    27.                 Mid$(PrintfEx, lPos, lSize) = Mid$(sText, lPrevIndex + 1, lSize)
    28.                 lPrevIndex = .FirstIndex + .Length
    29.                 sValue = A(Mid$(.Value, 2) - 1)
    30.                 Mid$(PrintfEx, lPos + lSize, Len(sValue)) = sValue
    31.                 lPos = lPos + lSize + Len(sValue)
    32.             End With
    33.         Next
    34.         lSize = Len(sText) - lPrevIndex
    35.         If lSize > 0 Then
    36.             Mid$(PrintfEx, lPos, lSize) = Mid$(sText, lPrevIndex + 1, lSize)
    37.         End If
    38.     End With
    39. End Function
    Same as dilettante's in priciple (single output string allocation) but based on RegExp. First calculates output string length, then in-place retrofits replacements.

    This one handles %NUM for any NUM, NUM is 1-based and % needs not be escaped.

    cheers,
    </wqw>

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width