What is ! and : used for in REXX - rexx

What does the ! and : do in REXX.
For instance in this piece of code
!all:!!=!;!=space(!);upper !;call !fid;!nt=right(!var('OS'),2)=='NT';!cls=word('CLS VMFCLEAR CLRSCREEN',1+!cms+!tso*2);if arg(1)\==1 then return 0;if wordpos(!,'? ?SAMPLES ?AUTHOR ?FLOW')==0 then return 0;!call=']$H';call '$H' !fn !;!call=;return 1
!cal:if symbol('!CALL')\=="VAR" then !call=;return !call
!env:!env='ENVIRONMENT';if !sys=='MSDOS'|!brexx|!r4|!roo then !env='SYSTEM';if !os2 then !env='OS2'!env;!ebcdic=1=='f0'x;return
!fid:parse upper source !sys !fun !fid . 1 . . !fn !ft !fm .;call !sys;if !dos then do;_=lastpos('\',!fn);!fm=left(!fn,_);!fn=substr(!fn,_+1);parse var !fn !fn '.' !ft;end;return word(0 !fn !ft !fm,1+('0'arg(1)))
!rex:parse upper version !ver !vernum !verdate .;!brexx='BY'==!vernum;!kexx='KEXX'==!ver;!pcrexx='REXX/PERSONAL'==!ver|'REXX/PC'==!ver;!r4='REXX-R4'==!ver;!regina='REXX-REGINA'==left(!ver,11);!roo='REXX-ROO'==!ver;call !env;return
!sys:!cms=!sys=='CMS';!os2=!sys=='OS2';!tso=!sys=='TSO'|!sys=='MVS';!vse=!sys=='VSE';!dos=pos('DOS',!sys)\==0|pos('WIN',!sys)\==0|!sys=='CMD';call !rex;return
!var:call !fid;if !kexx then return space(dosenv(arg(1)));return space(value(arg(1),,!env))
What is the !all:!!=! doing?
I actually have a lot of questions looking at this piece of code but I figured we would start there and see if that sheds some light on the rest.
The original code sample is located here http://rosettacode.org/wiki/Terminal_control/Coloured_text#REXX

As answered in the comments by Ryan Vincent:
The ! character is just another character you can use in 'variable names. So, instead of i in for loops you could use !. See the documentation and search for symbols.
The : is used at the end of a 'name' it indicate it is a 'label'. see: 12. Subroutines and functions. Trying to make sense of the 'optimized code that is shown will be 'interesting' but is possible. – Ryan Vincent Apr 18 at 19:55

Related

Why is $ split valid syntax? [duplicate]

I just discovered that perl ignores space between the sigil and its variable name and was wondering if someone could tell me if this was the expected behaviour. I've never run into this before and it can result in strange behaviour inside of strings.
For example, in the following code, $bar will end up with the value 'foo':
my $foo = 'foo';
my $bar = "$ foo";
This also works with variable declarations:
my $
bar = "foo\n";
print $bar;
The second case doesn't really matter much to me but in the case of string interpolation this can lead to very confusing behaviour. Anyone know anything about this?
Yes, it is part of the language. No, you should not use it for serious code. As for being confusing in interpolation, all dollar signs (that are not part of a variable) should be escaped, not just the ones next to letters, so it shouldn't be a problem.
I do not know if this is the real reason behind allowing whitespace in between the sigil and the variable name, but it allows you to do things like
my $ count = 0;
my $file_handle_foo = IO::File->new;
which might be seen by some people as handy (since it puts the sigils and the unique parts of the variable names next to each other). It is also useful for Obfu (see the end of line 9 and beginning of line 10):
#!/usr/bin/perl -w # camel code
use strict;
$_='ev
al("seek\040D
ATA,0, 0;");foreach(1..3)
{<DATA>;}my #camel1hump;my$camel;
my$Camel ;while( <DATA>){$_=sprintf("%-6
9s",$_);my#dromedary 1=split(//);if(defined($
_=<DATA>)){#camel1hum p=split(//);}while(#dromeda
ry1){my$camel1hump=0 ;my$CAMEL=3;if(defined($_=shif
t(#dromedary1 ))&&/\S/){$camel1hump+=1<<$CAMEL;}
$CAMEL--;if(d efined($_=shift(#dromedary1))&&/\S/){
$camel1hump+=1 <<$CAMEL;}$CAMEL--;if(defined($_=shift(
#camel1hump))&&/\S/){$camel1hump+=1<<$CAMEL;}$CAMEL--;if(
defined($_=shift(#camel1hump))&&/\S/){$camel1hump+=1<<$CAME
L;;}$camel.=(split(//,"\040..m`{/J\047\134}L^7FX"))[$camel1h
ump];}$camel.="\n";}#camel1hump=split(/\n/,$camel);foreach(#
camel1hump){chomp;$Camel=$_;y/LJF7\173\175`\047/\061\062\063\
064\065\066\067\070/;y/12345678/JL7F\175\173\047`/;$_=reverse;
print"$_\040$Camel\n";}foreach(#camel1hump){chomp;$Camel=$_;y
/LJF7\173\175`\047/12345678/;y/12345678/JL7F\175\173\0 47`/;
$_=reverse;print"\040$_$Camel\n";}';;s/\s*//g;;eval; eval
("seek\040DATA,0,0;");undef$/;$_=<DATA>;s/\s*//g;( );;s
;^.*_;;;map{eval"print\"$_\"";}/.{4}/g; __DATA__ \124
\1 50\145\040\165\163\145\040\157\1 46\040\1 41\0
40\143\141 \155\145\1 54\040\1 51\155\ 141
\147\145\0 40\151\156 \040\141 \163\16 3\
157\143\ 151\141\16 4\151\1 57\156
\040\167 \151\164\1 50\040\ 120\1
45\162\ 154\040\15 1\163\ 040\14
1\040\1 64\162\1 41\144 \145\
155\14 1\162\ 153\04 0\157
\146\ 040\11 7\047\ 122\1
45\15 1\154\1 54\171 \040
\046\ 012\101\16 3\16
3\15 7\143\15 1\14
1\16 4\145\163 \054
\040 \111\156\14 3\056
\040\ 125\163\145\14 4\040\
167\1 51\164\1 50\0 40\160\
145\162 \155\151
\163\163 \151\1
57\156\056

How to replace words after first two words

Let say i have the full name like: Wan Ahmad Wan Dollah Karmat.
And i want to display like: Wan Ahmad W.D.K
I tried this code:
preg_replace('/(.)[^\s]+\s?/', '${1}.', strtoupper($_GET['fullname']), 2)
But the output is: W.A.Wan Dollah Karmat
I want the first two words and shorter the rest words. please help.
Problem solved, thanks to Casimir et Hippolyte. The final code is:
preg_replace('~^(?:\s*\S+){1,2}(*SKIP)(*FAIL)|(\S)\S+~', '${1}.', strtoupper($_GET['fullname']))
its the matter of patterns.
You can use the backtracking control verbs (*SKIP) and (*FAIL) to avoid the two first words.
$pattern = '~^(?:\s*\S+){1,2}(*SKIP)(*FAIL)|(\S)\S+~';
$result = preg_replace_callback($pattern,
function ($m) { return strtoupper($m[1]) . '.'; },
$_GET['fullname'] );
In short:
(*SKIP) forces a substring that matches the preceding subpattern to not be retry if the pattern fails later.
(*FAIL) forces the pattern to fail.

How to parse variable in REXX/Regina

When writing a macro, I have a variable, {$#2}, that either starts with a 1 or 2 digit number followed by a ".", or it doesn't. When it starts in that way, I want to put the number into a rexxvar, which I have called C.
I have tried
#if [ DATATYPE(LEFT({$#2},1), "W") ] \
#evaluate ^^ ^parse '{$#2} C '.' .^ \
#endif \
This, and every variation I can think of, gives errors saying the #IF line contains invalid characters.
How should I do this?
I am using PPWizard, and Regina - but I can't create either tag.
Thanks
Ian
I do not use PPWizard so this could all be wrong, but
Looking at PPWizard #if, the if should be either
#if DATATYPE(LEFT({$#2},1), "W")
or
#if [ DATATYPE(LEFT({$#2},1), "W") <> 0 ]
But I do not know wether you can imbed the {$#2} or not (I do not know PPWizard)
For the parse statement one of these may be what you want
#evaluate ^^ ^parse value '{$#2}' with C '.' .^
or
#evaluate ^^ ^parse var {$#2} C '.' .^
See rexx parse syntax
An alternative way might try the Define Rexx tag and do it in rexx. More people could help you with pure rexx. i.e the rexx would be
if DATATYPE(LEFT(value_to_process,1), "W") then do
parse var value_to_process C '.'
end
where value_to_process is the value to be checked (i.e. {$#2})
For others.
The final answer to the problem is to write
#RexxVar value_to_process = {$#2}
#evaluate+ ^^ ^if DATATYPE(LEFT(value_to_process,1), "W") then do; parse var value_to_process C '.'; end^ \
in the macro I was creating.
Thanks Bruce. Your reply was most helpful on my route to a solution.

Handling multiple return values in ANTLR

I have a simple rule in ANTLR:
title returns [ElementVector<Element> v]
#init{
$v = new ElementVector<Element>() ;
}
: '[]'
| '[' title_args {$v.add($title_args.ele);} (',' title_args {$v = $title_args.ele ;})* ']'
;
with title_args being:
title_args returns [Element ele]
: author {$ele = new Element("author", $author.text); }
| location {$ele = new Element("location", $location.text); }
;
Trying to compile that I get confronted with a 127 error in the title rule: title_args is a non-unique reference.
I've followed the solution given to another similar question in this website (How to deal with list return values in ANTLR) however it only seems to work with lexical rules.
Is there a specific way to go around it ?
Thank you,
Christos
You have 2 title_args in your expression, you need to alias them. Try this:
| '[' t1=title_args {$v.add($t1.ele);} (',' t2=title_args {$v = $t2.ele ;})* ']'
t1 and t2 are arbitrary aliases you can choose anything you want as long as they match up.
I think the problem is your reusing the title_args var. Try changing one of those variable names.
Yeah, I had the same problem.
You need to change one of the variable names; for example, do like the following:
title_args
title_args1
in your code instead of using title_args twice.
If title_args is a parser rule, then just create the same rule with the name title_args1.
So, basically there would be two rules with the same functionality.

crystal reports : left() function outputs symbols?

When I run the following:
left({_v_kap.cpudesc}, (instr({_v_kap.cpudesc},",") ))
the function outputs : ¤¤Y¤ and other variations
however if I just run
left({_v_kap.cpudesc}, 48)
it returns the string correctly up to character 48
and if I just run
instr({_v_kap.cpudesc},",")
it returns 48
If I combine them, shouldn't this work?
any ideas?
Figured it out. If the instr() function doesn't find the item, the entire function bombs.
I checked the statement to see if its greater than zero. check if it runs, do it, otherwise don't check for the comma
pos := instr({_v_kap.cpudesc},",")
if pos > 0 then
left({_v_kap.cpudesc}, (instr({_v_kap.cpudesc},",") ))
else
{_v_kap.cpudesc}
this fixed the issue.
Phill,
In the code you provided one ")" is missing.
I believe it should be
left({_v_kap.cpudesc}, (instr({_v_kap.cpudesc},",") ) )
Thnks