concatenating unknown-length strings in COBOL - string

How do I concatenate together two strings, of unknown length, in COBOL? So for example:
WORKING-STORAGE.
FIRST-NAME PIC X(15) VALUE SPACES.
LAST-NAME PIC X(15) VALUE SPACES.
FULL-NAME PIC X(31) VALUE SPACES.
If FIRST-NAME = 'JOHN ' and LAST-NAME = 'DOE ', how can I get:
FULL-NAME = 'JOHN DOE '
as opposed to:
FULL-NAME = 'JOHN DOE '

I believe the following will give you what you desire.
STRING
FIRST-NAME DELIMITED BY " ",
" ",
LAST-NAME DELIMITED BY SIZE
INTO FULL-NAME.

At first glance, the solution is to use reference modification to STRING together the two strings, including the space. The problem is that you must know how many trailing spaces are present in FIRST-NAME, otherwise you'll produce something like 'JOHNbbbbbbbbbbbbDOE', where b is a space.
There's no intrinsic COBOL function to determine the number of trailing spaces in a string, but there is one to determine the number of leading spaces in a string. Therefore, the fastest way, as far as I can tell, is to reverse the first name, find the number of leading spaces, and use reference modification to string together the first and last names.
You'll have to add these fields to working storage:
WORK-FIELD PIC X(15) VALUE SPACES.
TRAILING-SPACES PIC 9(3) VALUE ZERO.
FIELD-LENGTH PIC 9(3) VALUE ZERO.
Reverse the FIRST-NAME
MOVE FUNCTION REVERSE (FIRST-NAME) TO WORK-FIELD.
WORK-FIELD now contains leading spaces, instead of trailing spaces.
Find the number of trailing spaces in FIRST-NAME
INSPECT WORK-FIELD TALLYING TRAILING-SPACES FOR LEADING SPACES.
TRAILING-SPACE now contains the number of trailing spaces in FIRST-NAME.
Find the length of the FIRST-NAME field
COMPUTE FIELD-LENGTH = FUNCTION LENGTH (FIRST-NAME).
Concatenate the two strings together.
STRING FIRST-NAME (1:FIELD-LENGTH – TRAILING-SPACES) “ “ LAST-NAME DELIMITED BY SIZE, INTO FULL-NAME.

You could try making a loop for to get the real length.

Related

Excel Formula To Replicate Text To Column Functionality

I would like a formula in excel that does what Text To Columns does.
For example the following string in A1
" text with a comma, stays in one column",," keep starting blank text",1,2,3,"123"
Would be split into multiple cells like this...
The following LET Function allows you to split the text into columns based on the splitter character (in this instance a comma).
It ignores commas that are between quotes (the Delim argument - which has double quotes in it).
It does this by ensuring there is an even number of quotes before the splitter character.
=LET(
NOTES,"Splits a string but also checks to see if the splitter is inside a delimiter. So will ignore a comma inside quotes.",
RawString,$A1,
Splitter,",",Note2,"This is the character to split the string by",
Delim,"""",Note4,"This is the text delimiter it looks odd but it's just a double quote - change to "" if you don't want text delimitation",
IgnoreBlanks,FALSE,
CleanTextDelims,TRUE,
TrimBlanks,FALSE,
SplitString,Splitter&RawString&Splitter,Note3,"Add the splitter to the start and the end to help create the array of split positions",
StringLength,LEN(SplitString),
Seq,SEQUENCE(1,StringLength),Note5,"Get a sequence from 1 to the length of the split string",
Note6,"The below does the bulk of the work. It works out if we are at an odd or even point in terms of count of text delimiters up to the point in the sequence we are processing.",
Note7,"if we are at an even point and we have a delimiter then make a note of the sequence otherwise put a blank.",
PosArray,IF(Seq=StringLength,Seq,IF(MOD(LEN(LEFT(SplitString,Seq))-LEN(SUBSTITUTE(LEFT(SplitString,Seq),Delim,"")),2)=0,IF(MID(SplitString,Seq,1)=Splitter,Seq,""),"")),
PosArrayClean,FILTER(PosArray,PosArray<>""),Note8,"Clean blanks",
StartArray,FILTER(PosArrayClean,PosArrayClean<>StringLength),
EndArray,FILTER(PosArrayClean,PosArrayClean<>1),
StringArray,MID(SplitString,StartArray+1,EndArray-StartArray-1),
StringArrayB,IF(IgnoreBlanks,FILTER(StringArray,StringArray<>""),StringArray),
StringArrayC,IF(CleanTextDelims,IF(LEFT(StringArrayB,1)=Delim,MID(StringArrayB,2,IF(RIGHT(StringArrayB,1)=Delim,LEN(StringArrayB)-2,LEN(StringArrayB))),StringArrayB),StringArrayB),
IFERROR(IF(TrimBlanks,TRIM(StringArrayC),StringArrayC),"")
)
Breaking down each step in the LET formula:
Supply the raw string (from cell A1 in this case)
Set the splitter character - in this case a comma
Set the text delimiter - in this case double quotes (looks odd because it has to be as double double quotes - Delim,"""" )
IgnoreBlanks is an option to exclude blank cells in the output
CleanTextDelims will clean the TextDelimiter (Double quotes) from the start and end of the resultant string
Create a SplitString variable with the split character at the front and back.
Get the length of the string for ease of use
Get a sequence from 1 to the length of the string.
Get an array of the position of characters that are splitters with an even number of Text Delimiters to the left of that position in the string the posArray (splitter position array).
Clean the blanks to get the posArrayClean
Create a start and end array (start array ignores the last and end array ignores the first item in the PosArrayClean)
Get the array of strings/cells to output.
If the IgnoreBlanks is used then igore blank cells
If the CleanTextDelims option is set then strip off the Text Delim (double quotes) from the start and end of the resultant string.
If the TrimBlanks option is set then trim blank spaces off the start and end of the resulting strings.
Hopefully the notes explain clearly how this works and make it easy to modify.
If you want create a named Lambda to use you can use the following code to paste into the formula of a named range called SplitStringDelim (you can name it what you like of course). NB You can't have the line separators in this and I stripped the notes out of it.
=LAMBDA(StringRaw,SplitChar,DelimChar,IgnoreBlank,CleanTextDelim,TrimBlank, LET( RawString,StringRaw, Splitter,SplitChar, Delim,DelimChar, IgnoreBlanks,IgnoreBlank, CleanTextDelims,CleanTextDelim, TrimBlanks,TrimBlank, SplitString,Splitter&RawString&Splitter, StringLength,LEN(SplitString), Seq,SEQUENCE(1,StringLength), PosArray,IF(Seq=StringLength,Seq,IF(MOD(LEN(LEFT(SplitString,Seq))-LEN(SUBSTITUTE(LEFT(SplitString,Seq),Delim,"")),2)=0,IF(MID(SplitString,Seq,1)=Splitter,Seq,""),"")), PosArrayClean,FILTER(PosArray,PosArray<>""),Note8,"Clean blanks", StartArray,FILTER(PosArrayClean,PosArrayClean<>StringLength), EndArray,FILTER(PosArrayClean,PosArrayClean<>1), StringArray,MID(SplitString,StartArray+1,EndArray-StartArray-1), StringArrayB,IF(IgnoreBlanks,FILTER(StringArray,StringArray<>""),StringArray), StringArrayC,IF(CleanTextDelims,IF(LEFT(StringArrayB,1)=Delim,MID(StringArrayB,2,IF(RIGHT(StringArrayB,1)=Delim,LEN(StringArrayB)-2,LEN(StringArrayB))),StringArrayB),StringArrayB), IFERROR(IF(TrimBlanks,TRIM(StringArrayC),StringArrayC),"")))

Is there a way to add leading/trailing spaces to item in concatenate function?

I am trying to bring together several cells and they have a specific length so if I have
A1 needs to be 5 chars and the value is 'cat'
B1 needs to be 6 chars and the value is 'dog'
Concatenated it would be:
[space space]cat[space space space]dog
or
" cat dog"
I'm having trouble finding a function or set of functions that allows this, most want to trim out leading or trailing spaces.
Yes:
=CONCATENATE(RIGHT(REPT(" ",5)&A1,5),RIGHT(REPT(" ",6)&A2,6))
or as #BigBen stated use & instead of Concatenate:
=RIGHT(REPT(" ",5)&A1,5)&RIGHT(REPT(" ",6)&A2,6)

Is there a function to remove alphanumeric words given a sentence using python

Given a sentence "hi I stay at 4th cross street and my ssn number is 56tyuh". I want to remove words such as alphanumeric ( 4th and 56tyuh ). Does isalpha() is used only to check if there are alphanumerics in sentences? If not how do I use it to remove alphanumerics
You'll need to use regex for this. Regex can be confusing but in this case, it's quite straight forward.
import re
s = 'hi I stay at 4th cross street and my ssn number is 56tyuh'
r = r'\S*\d+\S*'
cut_string = re.sub(r, '', s)
Let's break this down:
r is a regex variable, which detects character sequences of 0-n leading non-whitespace characters, followed by 1-n numeric charcters and again 0-n trailing non-whitespace characters.
re.sub replaces the matches of our regex with the second parameter, in our case an empty string. Thus it removes all matches of our regex from the string.
Edit:
This will also remove numbers. If you only want to remove alphanumeric words, make the follwing change:
r = r'([a-zA-Z]*\d+[a-zA-Z]+|[a-zA-Z]+\d+[a-zA-Z]*)'
Note the | in the center of the variable. This means either match the first part within the parentheses or the second. The first would match 4th but not ep95, the opposite is true for the second.

How to Find a word with spaces in livecode

How to find a word with space (eg: i want to find a word "X1 X2 X3"). I am using the following code
put the text of field "f4" into xx
find xx in field "f1"
In LiveCode, the space character delimits words -- a single word doesn't contain spaces. If there's only one instance of the string of characters you're searching for, you could use the offset function:
put "X1 X2 X3" into theString
put the text of fld "f4" into temp
put offset(theString,temp) into theNum
The variable theNum will contain the number of characters before the first character of the string, or will contain 0 if the string is not found in the field's text.

remove only decimal place and not comma

Please i have 123,788.98, I want to remove the decimal place before storing in dbase so as to have just 123,789.
I tried round(123,789.98) but it gives me just 123.
Please how can remove the decimal place without removing the comma?
Divided with comma, these are two numbers. 123 and 788.98. So just round(788.98) and insert them both in one row.
INSERT INTO table(row) VALUES ('123,'.round(788.98).'')
If you have a comma, you can create two variables from the form input:
list($one, $two) = explode(",", "S_POST['amount']", 2);

Resources