VBA Split a String in two parts - vba

I'm trying to obtain two codes from this string: "HL PNX-70[15200]"
But with this code, I obtain two times the same output: "HL PNX-70". So, the code is not properly done.
How to obtain the output '15200' from the above mentioned String?
Code:
Private Sub Comando221_Click()
MsgBox (Right(Split("HL PNX-70[15200]", "[")(0), 50))
MsgBox (Left(Split("HL PNX-70[15200]", "[")(0), 50))
End Sub

Are you looking for this ?
Sub Test()
MsgBox Split("HL PNX-70[15200]", "[")(0)
MsgBox Replace(Split("HL PNX-70[15200]", "[")(1), "]", "")
End Sub

Split returns a zero-based array so you are interested in the second element, index 1. Both lines of your code are extracting "HL PNX-70" and the leftmost and rightmost 50 characters will clearly be the same.
This code illustrates two ways of extracting the desired string for your specific example, but it is not necessarily ironclad if you are working with multiple different types of string. You could also use Instr, as per the other answer, or look at regular expressions if you need more complex pattern matching.
Sub y()
Dim s As String, v
s = "HL PNX-70[15200]"
v = Split(s, "[")
Debug.Print v(0) 'HL PNX-70
Debug.Print v(1) '15200]
MsgBox Left(v(1), Len(v(1)) - 1) '15200
v = Split(v(1), "]")
MsgBox v(0) '15200
End Sub

You could try:
Option Explicit
Sub Test()
Dim str As String, Result As String
Dim Start_Point As Long, No_Characters As Long
str = "HL PNX-70[15200]"
Start_Point = InStr(str, "[") + 1
No_Characters = Len(str) - Start_Point
Result = Mid(str, Start_Point, No_Characters)
Debug.Print Result
End Sub

Here is your code
Dim text, text1, text2 As String
text = "HL PNX-70[15200]"
text1 = Break_String(CStr(text), 0)
text2 = Break_String1(Break_String(CStr(text), 1))
Function Break_String(a As String, pos As Integer) As String
Dim WrdArray() As String
WrdArray() = Split(a, "[")
Break_String = WrdArray(pos)
End Function
Function Break_String1(a As String) As String
Dim WrdArray() As String
WrdArray() = Split(a, "]")
Break_String1 = WrdArray(0)
End Function

Related

VB code to remove special character in a column

I am having a column which contains integer values with two special character "," and "_". I am trying to remove these character for example 1,10_2,2_3,3 should be like 1102233. Thanks in advance for your suggestions.
this function isn't foolproof but it is a good start.
Function trim(aStringToTrim As String, aElementToTrinm() As Variant) As String
Dim elementToTrim As Integer
Dim IndexInString As Integer
For elementToTrim = LBound(aElementToTrinm) To UBound(aElementToTrinm)
IndexInString = InStr(aStringToTrim, aElementToTrinm(elementToTrim))
Do While IndexInString > 0
aStringToTrim = Left(aStringToTrim, IndexInString - 1) & Right(aStringToTrim, Len(aStringToTrim) - IndexInString - Len(aElementToTrinm(elementToTrim)) + 1)
IndexInString = InStr(aStringToTrim, aElementToTrinm(elementToTrim))
Loop
Next
End Function
It can be use like this:
Sub main()
Dim myString As String
Dim caracterstoRemove As Variant
caracterstoRemove = Array(",", ".")
myString = "This, is. a, string, with. caracters to remove."
myString = trim(myString, caracterstoRemove)
End Sub

Spliting a string in VBA to get a list of numeric values

I would like to split the following string "2/3/4/4" for example and get each number and save them as a list.
I can split the string with the code split("2/3/4/4", "/") but then I cannot manage to put them in a list.
Any help is appreciated.
Yes, like engineersmnky says you can just return the results of Split() to a String array, like this:
Public Sub Test()
Dim results() As String
Dim i As Integer
results = Split("2/3/4/4", "/")
For i = LBound(results) To UBound(results)
MsgBox results(i)
Next i
End Sub
This would split "2/3/4/4" and put the numbers in A1:A4
Sub SplitAndList()
Dim nums As Variant, n As Integer
nums = Split("2/3/4/4", "/")
For n = 0 To UBound(nums)
Range("A" & n + 1) = nums(n)
Next n
End Sub

Handling series of comma separated values in VBA

I have this function which returns as string the value in comma separated string which is in order of given integer value.
Private Sub TestGetNthNumber()
Debug.Print GetNthNumber("NUMBERS 5088, 5089, 5090, 5091", 2)
End Sub
Public Function GetNthNumber(sMark As String, iOrder As Integer) As String
Dim sTemp As String
Dim sNumber As String
Dim iLoop As Integer
If sMark = "" Then
Exit Function
End If
sTemp = sMark & ","
For iLoop = 1 To iOrder
sTemp = Mid(sTemp, InStr(sTemp, " "))
sNumber = Trim(Left(sTemp, InStr(sTemp, ",") - 1))
sTemp = Mid(sTemp, InStr(sTemp, ",") + 1)
Next
GetNthNumber = sNumber
End Function
The test Sub will return "5089" as its given number 2 in the list of values.
My question;
Is there better method to do this instead of the messy string manipulation with Mid, Left and InStr? Like a way to turn the comma separated string values into an array?
Another problem;
It is possible the string is in format "NUMBERS 5088, 5089, 5090 and 5091". But for this I assume simply replacing " and" with "," before handling it does the trick.
The other alternative is to use RegEx/RegExp. Your function will looks like that:
Public Function GetNthNumberAlternative(sMark As String, iOrder As Integer) As String
'regexp declaration
Dim objRegExp As Object
Set objRegExp = CreateObject("vbscript.regexp")
With objRegExp
.Global = True
.Pattern = "\d+"
GetNthNumberAlternative = .Execute(sMark)(iOrder - 1).Value
End With
End Function
And you could call it in this way:
Private Sub TestGetNthNumber()
Debug.Print GetNthNumberAlternative("NUMBERS 5088 AND 5089 OR 5090, 5091", 1)
End Sub
You want to use the Split function. If you have the same values each time then you can remove the NUMBERS and the final AND. Something like this:
Private Sub TestGetNthNumber()
Debug.Print GetNthNumber("NUMBERS 5088, 5089, 5090, 5091", 2)
End Sub
Public Function GetNthNumber(sMark As String, iOrder As Integer) As String
Dim vArray As Variant
sMark = Replace(sMark, "NUMBERS", "")
sMark = Replace(sMark, "AND", "")
vArray = Split(sMark, ",")
GetNthNumber = vArray(iOrder)
End Function

Search for a certain style in word 2010 and make it into a bookmark using vba

How to make a style as a bookmark in word 2010?
You won't be able to use most of the text in the document as the bookmark name. It is just illegal to use certain characters in a bookmark name in Word/VBA. It may be possible to add such characters in bookmark names in an XML format of the document, so if it is required, you can ask a separate question.
This feels like way too much code to post on SO. You really need to explain what framework you have in place and tell us where your hurdles are. We can't do this again. "Works for me". If you have any questions though don't hesitate to ask.
Run the "RunMe" macro at the bottom.
Private Function IsParagraphStyledWithHeading(para As Paragraph) As Boolean
Dim flag As Boolean: flag = False
If InStr(1, para.Style, "heading", vbTextCompare) > 0 Then
flag = True
End If
IsParagraphStyledWithHeading = flag
End Function
Private Function GetTextRangeOfStyledParagraph(para As Paragraph) As String
Dim textOfRange As String: textOfRange = para.Range.Text
GetTextRangeOfStyledParagraph = textOfRange
End Function
Private Function BookmarkNameAlreadyExist(bookmarkName As String) As Boolean
Dim bookmark As bookmark
Dim flag As Boolean: flag = False
For Each bookmark In ActiveDocument.Bookmarks
If bookmarkName = bookmark.name Then
flag = True
End If
Next
BookmarkNameAlreadyExist = flag
End Function
Private Function CreateUniqueBookmarkName(bookmarkName As String)
Dim uniqueBookmarkName As String
Dim guid As String: guid = Mid$(CreateObject("Scriptlet.TypeLib").guid, 2, 36)
guid = Replace(guid, "-", "", , , vbTextCompare)
uniqueBookmarkName = bookmarkName & guid
CreateUniqueBookmarkName = uniqueBookmarkName
End Function
Private Function BookmarkIt(rng As Range, bookmarkName As String)
Dim cleanName As String: cleanName = MakeValidBMName(bookmarkName)
If BookmarkNameAlreadyExist(cleanName) Then
cleanName = CreateUniqueBookmarkName(cleanName)
End If
ActiveDocument.Bookmarks.Add name:=cleanName, Range:=rng
End Function
''shamelessly stolen from gmaxey at http://www.vbaexpress.com/forum/showthread.php?t=37674
Private Function MakeValidBMName(strIn As String)
Dim pFirstChr As String
Dim i As Long
Dim tempStr As String
strIn = Trim(strIn)
pFirstChr = Left(strIn, 1)
If Not pFirstChr Like "[A-Za-z]" Then
strIn = "A_" & strIn
End If
For i = 1 To Len(strIn)
Select Case Asc(Mid$(strIn, i, 1))
Case 49 To 58, 65 To 90, 97 To 122
tempStr = tempStr & Mid$(strIn, i, 1)
Case Else
tempStr = tempStr & "_"
End Select
Next i
tempStr = Replace(tempStr, " ", " ")
MakeValidBMName = tempStr
End Function
Sub RunMe()
Dim para As Paragraph
Dim textOfPara As String
For Each para In ActiveDocument.Paragraphs
If IsParagraphStyledWithHeading(para) Then
textOfPara = GetTextRangeOfStyledParagraph(para)
If para.Range.Bookmarks.Count < 1 Then
BookmarkIt para.Range, textOfPara
End If
End If
Next
End Sub

VBA. How to find position of first digit in string

I have string "ololo123".
I need get position of first digit - 1.
How to set mask of search ?
Here is a lightweight and fast method that avoids regex/reference additions, thus helping with overhead and transportability should that be an advantage.
Public Function GetNumLoc(xValue As String) As Integer
For GetNumLoc = 1 To Len(xValue)
If Mid(xValue, GetNumLoc, 1) Like "#" Then Exit Function
Next
GetNumLoc = 0
End Function
Something like this should do the trick for you:
Public Function GetPositionOfFirstNumericCharacter(ByVal s As String) As Integer
For i = 1 To Len(s)
Dim currentCharacter As String
currentCharacter = Mid(s, i, 1)
If IsNumeric(currentCharacter) = True Then
GetPositionOfFirstNumericCharacter = i
Exit Function
End If
Next i
End Function
You can then call it like this:
Dim iPosition as Integer
iPosition = GetPositionOfFirstNumericCharacter("ololo123")
Not sure on your environment, but this worked in Excel 2010
'Added reference for Microsoft VBScript Regular Expressions 5.5
Const myString As String = "ololo123"
Dim regex As New RegExp
Dim regmatch As MatchCollection
regex.Pattern = "\d"
Set regmatch = regex.Execute(myString)
MsgBox (regmatch.Item(0).FirstIndex) ' Outputs 5
I actually have that function:
Public Function GetNumericPosition(ByVal s As String) As Integer
Dim result As Integer
Dim i As Integer
Dim ii As Integer
result = -1
ii = Len(s)
For i = 1 To ii
If IsNumeric(Mid$(s, i, 1)) Then
result = i
Exit For
End If
Next
GetNumericPosition = result
End Function
You could try regex, and then you'd have two problems. My VBAfu is not up to snuff, but I'll give it a go:
Function FirstDigit(strData As String) As Integer
Dim RE As Object REMatches As Object
Set RE = CreateObject("vbscript.regexp")
With RE
.Pattern = "[0-9]"
End With
Set REMatches = RE.Execute(strData)
FirstDigit = REMatches(0).FirstIndex
End Function
Then you just call it with FirstDigit("ololo123").
If speed is an issue, this will run a bit faster than Robs (noi Rob):
Public Sub Example()
Const myString As String = "ololo123"
Dim position As Long
position = GetFirstNumeric(myString)
If position > 0 Then
MsgBox "Found numeric at postion " & position & "."
Else
MsgBox "Numeric not found."
End If
End Sub
Public Function GetFirstNumeric(ByVal value As String) As Long
Dim i As Long
Dim bytValue() As Byte
Dim lngRtnVal As Long
bytValue = value
For i = 0 To UBound(bytValue) Step 2
Select Case bytValue(i)
Case vbKey0 To vbKey9
If bytValue(i + 1) = 0 Then
lngRtnVal = (i \ 2) + 1
Exit For
End If
End Select
Next
GetFirstNumeric = lngRtnVal
End Function
An improved version of spere's answer (can't edit his answer), which works for any pattern
Private Function GetNumLoc(textValue As String, pattern As String) As Integer
For GetNumLoc = 1 To (Len(textValue) - Len(pattern) + 1)
If Mid(textValue, GetNumLoc, Len(pattern)) Like pattern Then Exit Function
Next
GetNumLoc = 0
End Function
To get the pattern value you can use this:
Private Function GetTextByPattern(textValue As String, pattern As String) As String
Dim NumLoc As Integer
For NumLoc = 1 To (Len(textValue) - Len(pattern) + 1)
If Mid(textValue, NumLoc, Len(pattern)) Like pattern Then
GetTextByPattern = Mid(textValue, NumLoc, Len(pattern))
Exit Function
End If
Next
GetTextByPattern = ""
End Function
Example use:
dim bill as String
bill = "BILLNUMBER 2202/1132/1 PT2200136"
Debug.Print GetNumLoc(bill , "PT#######")
'Printed result:
'24
Debug.Print GetTextByPattern(bill , "PT#######")
'Printed result:
'PT2200136