I want to catch content between two $ symbols.
Eg: - This is $ only$ an example $so$ respond $quickly$.
Here I want to store text between dollars (only, so and quickly) into an array.
In using this code for catching. But it catches (only, an example, so, respond, quickly). I need "only", "so" and "quickly".
replace "\$" with "\XXdollarXX" in field "MytextField"
put the text of field "MytextField" into ss
repeat with i = 0 to the number of chars in ss
if char i of ss contains "$" then
repeat with x = i+1 to the number of chars in ss
if char x of ss contains "$" then
--answer x
put x into Lpos
put char i to Lpos of ss into jar
answer jar
put Lpos into i
end if
end repeat
end if
end repeat
If you examine your code while stepping through, you will see this has to work that way. The "offset" function, though, can be used in a loop, and contains a parameter "chars to skip". By continuously updating that parameter, and considering that only every other instance is pertinent, you can collect the text between the pairs of "$" as:
between instance 1 and 2
between instance 3 and 4
etc.
Make a button and a field. Put some text into the field sprinkled with "$" for testing. In the button script:
on mouseUp
put 0 into charsToSkip
repeat until charsToskip > the length of fld 1
if the optionKey is down then exit to top --YOU WILL NEED THIS RIGHT NOW...
get offset("$",fld 1,charsToSkip)
add it to charsToSkip
put charsToSkip & return after accum
end repeat
end mouseUp
I leave it to you to add the ability to exit this loop properly. Step through the handler and you will see the value in accum building in the way I mentioned.
Craig Newman
Related
I have some data with strings, and I want to flag when a word is found. A word would be defined as at the start of the string, end, or separated a space. strpos will find whenever the string is present, but I am looking for something similar to subinword. Does Stata have a way to use the functionality of subinword without having to replace it, and instead flag the word?
clear
input id str50 strings
1 "the thin th man"
2 "this old then"
3 "th to moon"
4 "moon blank th"
end
gen th_pos = 0
replace th = 1 if strpos(strings, "th") >0
This above code will flag every observation as they all contain "th", but my desired output is:
ID strings th_sub
1 "the thin th man" 1
2 "this old then" 0
3 "th to moon" 1
4 "moon blank th" 1
A small trick is that "th" as a word will be preceded and followed by a space, except if it occurs at the beginning or the end of string. The exceptions are no challenge really, as
gen wanted = strpos(" " + strings + " ", " th ") > 0
works around them. Otherwise, there is a rich set of regular expression functions to play with.
The example above flags that the code that doesn't do what you want condenses to one line,
gen th_pos = strpos(strings, "th") > 0
A more direct answer is that you don't have to replace anything. You just have to get Stata to tell you what would happen if you did:
gen WANTED = strings != subinword(strings, "th", "", .)
If removing a substring if present changes the string, it must have been present.
Regular expressions can be useful for this type of exercise, with word boundaries allowing you to search for whole words indicated by \b, as in "\bword\b".
gen wanted = ustrregexm(strings, "\bth\b")
I need a code on AHK
I have a variable look like this:
CYOMYACHOAYJGUGRYYQNYB
I need to get this:
YMAHAJURYNB
I meen, i need every second char from a variable. Thank in advance
Var := "CYOMYACHOAYJGUGRYYQNYB"
Loop, Parse, Var ; retrieves each character from the variable, one at a time
{
If (Mod(A_Index, 2) = 0) ; If A_Index is even (the remainder after division by 2 is 0)
NewVar .= A_LoopField ; add the retrieved character to the new variable
}
MsgBox %NewVar%
This works for me. I am using bit wise to determine if the index of the array of letters, given to me by StrSplit(TestString), is even or odd as I loop through them. I used this forum post for the bitwise logic. Then I concatenate if the line is even. So if index&1=0 will be true when the number is even, thus giving me every other letter to concatenate into NewString with this line NewString=%NewString%%letter%. Feel free to uncomment out the message box lines by removing the ; to better see how the loop parses the array.
TestString := "ABCD"
word_array := StrSplit(TestString)
NewString:=""
For index, letter in word_array{
if index&1=0
{
;MsgBox, %letter% added
NewString=%NewString%%letter%
;Msgbox, %NewString%
}
}
MsgBox, %NewString%
As you don't specify any language, I'll answer in pseudocode:
set counter to 1
set result to empty string
for every char in string:
if counter is even:
append char to result
increment counter by 1
user3419297 beat me to it, but mine is even easier:
InputBox, x, What Variable?, Enter Variable:
loop, % StrLen(x)
If mod(A_Index,2)=0
y.=substr(x,A_Index,1)
msgbox %y%
Clipboard := y
You input the variable in a dialog, and the result is shown, and put in clipboard. Hth,
EDIT: I like the bitwise logic from Zack Tarr! Substitute for the "if" above:
If A_Index&1=0
The rest is the same.
I am presently working on a file to open one by one .txt documents, extract data, to finally fill a .excel document.
Because I did not know how it is possible to write multiple times on the same line of my Excel document after one write statement (because it jumps to the next line), I have created a string of characters which is filled time after time :
Data (data_limite(x),x=1,8)/10, 9, 10, 7, 9, 8, 8, 9/
do file_descr = 1,nombre_fichier,1
taille_data1 = data_limite(file_descr)
nvari = taille_data1-7
write (new_data1,"(A30,A3,A11,A3,F5.1,A3,A7,F4.1,<nvari>(A3))") description,char(9),'T-isotherme',char(9),T_trait,char(9),'d_gamma',taille_Gam,(char(9),i=1,nvari)
ecriture_descr = ecriture_descr//new_data1
end do
Main issue was I want to adapt char(9) amount with the data_limite value so I built a write statement with a variable amount of char(9).
At the end of the do-loop, I have a very complex format of ecriture_descr which has no periodic format due to the change of the nvari value
Now I want to add this to the first line of my .excel :
Open(Unit= 20 ,File='resultats.RES',status='replace')
write(20,100) 'param',char(9),char(9),char(9),char(9),char(9),'*',char(9),'nuances',char(9),'*',char(9),ecriture_descr
100 format (a5,5(a3),a,a3,a7,a,a3,???)
but I do not know how to write this format. It would have been easier if, at each iteration of the do-loop I could fill the first line of my excel and continue to fill the first line at each new new_data1 value.
EDIT : maybe adding advance='no' in my write statement would help me, I am presently trying to add it
EDIT 2 : it did not work with advance='no' but adding a '$' at the end of my format write statement disable the return of my function. By moving it to my do-loop, I guess I can solve my problem :). I am presently trying to add it
First of all, your line
ecriture_descr = ecriture_descr//new_data1
Is almost certainly not doing what you expect it to do. I assume that both ecriture_descr and new_data are of type CHARACTER(len=<some value>) -- that is a fixed length string. If you assign anything to such a string, the string is cut to length (if the assigned is too long), or padded with spaces (if the assigned is too short:
program strings
implicit none
character(len=8) :: h
h = "Hello"
print *, "|" // h // "|" ! Prints "|Hello |"
h = "Hello World"
print *, "|" // h // "|" ! Prints "|Hello Wo|"
end program strings
And this combination will work against you: ecriture_descr will already be padded to the max with spaces, so when you append new_data1 it will be just outside the range of ecriture_descr, a bit like this:
h = "Hello" ! h is actually "Hello "
h = h // "World" ! equiv to h = "Hello " // "World"
! = "Hello World"
! ^^^^^^^^^
! Only this is assigned to h => no change
If you want a string aggregator, you need to use the trim function which removes all trailing spaces:
h = trim(h) // " World"
Secondly, if you want to write to a file, but don't want to have a newline, you can add the option advance='no' into the write statement:
do i = 1, 100
write(*, '(I4)', advance='no') i
end do
This should make your job a lot easier than to create one very long string in memory and then write it all out in one go.
I have a scrolling field. It's containing some text and special characters like (---,'',.,",) e.t.c. I want add a single space before every special characters.Is it possible
I d not know how long your text is, but you can:
on mouseUp
get fld "yourField"
put "abcdefghijklmnopqrstuvwxyz" into normalChars
repeat for each char tChar in it
if tChar is not in normalChars then put space & tChar after temp
else put tChar after temp
end repeat
put temp into fld "yourOtherField"
end mouseUp
Now this assumes that all non-letter chars are "special" chars. Can you modify the handler to go the other way? That is, to identify only certain chars, rather than identify all non-letter chars?
Craig Newman
ya. Please use this code
replace "--" with " --" in field "yourField"
replace "---" with " ---" in field "yourField"
Morning guys.
I made a Label Generator in Excel, on which I converted the items chosen in dropdown lists to leters which translate to these items chosen.
This convertion is quite simple.
If tipoChosen = "UTP" Then
tipo = "U"
End If
This happens for every user input about the label.
I also had to add a number that made each label different, so I made this line:
FinalLabel = tipo & forn & Format(Nextrow - 2, "00000") & "." & Color & "(" & metragem & ")"
Where the "Format(Nextrow - 2, "00000")" Would give me a number depending on which row it was, beggining in 00000 and going through infinity and beyond(until long capacity ended). This worked and I was happy with it.
My boss just told me that what I did was wrong, and that it needs to reset this number for each type of cable. Meaning that
if all the other parameters stay the same, it keeps counting.
If it changes it goes back to 00000
If it goes back to whatever type I already used, it keeps counting from the previous number.
And I honestly have no clue on how to do this the way I made my code. Will I need to do it from scratch and work my way around this? Or is there a way to implement this feature as it is?
Edit: I also have numerical inputs, things such as the lenght of the cable, thing that will change the label. Meaning that there needs to be a "check" to see if that lenght was also used before. Remember that:
if ALL parameters are identical, keep counting from 00000 to whatever labels are to create. (let's say 00100)
if something changes it starts from 00000
if it goes back to a previous used combination of parameters it KEEPS counting from whatever number it was previously. (meaning the next one would be 00101)
You can definitely rework what you have already.
You'll need to add a counter variable for each type, to keep track of the count. Set these counters to 0 at the start of your code.
Easiest method: Dim an array with an element for each type, which will contain the counter for that type:
Dim i
Dim Counter(1 To 5) As Integer
For i = 1 to 5
Counter(i).Value = 0
Next i
Each time you change your type, update the counter index (i). You could use a select statement here to set tipo & Counter index (i):
Select Case tipoChosen
Case "UTP"
tipo = "U"
i = 1
Case "otherType"
tipo = "X"
i = 2
// etc...
End Select
Then increment Counter for each iteration, until the type changes.
FinalLabel = tipo & forn & Format(Counter(i).value, "00000") & "." &
Color & "(" & metragem & ")"
Counter(i).value = Counter(i).value + 1
There are better ways to do this, but this is probably the easiest solution. If you want the more complex approach, go with dynamic variable names, or using a pointer from main counter to type counter but that’s more complicated….