Decrement or increment a variable in the robot framework - variables

I just want to decrement the variable N_groups in the last line.
This is my robot file:
Preconditions - Delete Groups But Not First
${N_groups} Setup Groups Count Groups
Log to console N_groups: ${N_groups}
: FOR ${INDEX} IN RANGE 1 20
\ Run Keyword If '${N_groups}' == '1' Exit For Loop
\ Setup Groups Delete Group ${group}
\ ${N_groups}= ${N_groups}-1
I get the error:
No keyword with name '${N_groups}-1' found.
What I am doing wrong here?

Try putting it inside the var name. i.e.
${N_groups-1}

If the variable is already a number, you can use:
${N_groups}= ${N_groups-1}
To do this you need to coerce it to a number (otherwise you'll get an error saying failed: TypeError: coercing to Unicode: need string or buffer, int found), e.g.
*** Variables ***
${N_groups}= ${0} # ${} notation coerces value to a number
Alternatively, you can use Evaluate like this, which works whether ${N_groups} has been coerced to a number or not:
${N_groups}= Evaluate ${N_groups} - 1

Try this:
${decrement_counter}= set variable 1
-- inside the loop
${N_groups}= Evaluate ${N_groups} - ${decrement_counter}
Note - only one space before and after subtraction sign.

Related

Value - ask-API-v1.0.7. Value must increment like ask-API-v1.0.8 ,ask-API-v1.0.9 and so on. Pls get me syntax using awk

Value - ask-API-v1.0.7.
Value must increment like ask-API-v1.0.8 ,ask-API-v1.0.9 and so on.
Please get me syntax using awk
Expectation -ask-API-v1.0.8 ,ask-API-v1.0.9 and so on

Robotframework - returned value of Evaluate keyword does not store all numeric values in variable

I'm trying to compute for a value using Evaluate keyword and it seems not storing the exact whole numeric numbers in the variable ${C1} but it seems to return the exact values I want as per log file.
Here's my sample code.
${C1} Evaluate 1.025**${C_IP_Years_Between}
Here's the log:
${C1} = BuiltIn . Evaluate 1.025**${C_IP_Years_Between}
Documentation:
Evaluates the given expression in Python and returns the results.
Start / End / Elapsed: 20180413 21:09:18.343 / 20180413 21:09:18.377 / 00:00:00.034
21:09:18.345 TRACE Arguments: [ '1.025**11' ]
21:09:18.376 TRACE Return: 1.3120866578012655
21:09:18.377 INFO ${C1} = 1.3120866578
How can I be able to use the whole values being returned above (e.g. 1.3120866578012655)
The robot variable ${C1} is a float, so it retains all of the precision. The log statement is simply not showing all of the digits.
You can see all of the digits if you explicitly convert the value to a string. In the following example, the test should pass:
*** Variables ***
${C_IP_Years_Between} 11
*** Test Cases ***
Example
${C1}= Evaluate 1.025**${C_IP_Years_Between}
${C1f}= Evaluate '{0:.16f}'.format($c1)
Should be equal as strings ${C1f} 1.3120866578012655

Variable substitution within braces in Tcl

Correct me wherever I am wrong.
When we use the variables inside braces, the value won't be replaced during evaluation and simply passed on as an argument to the procedure/command. (Yes, some exception are there like expr {$x+$y}).
Consider the following scenarios,
Scenario 1
% set a 10
10
% if {$a==10} {puts "value is $a"}
value is 10
% if "$a==10" "puts \"value is $a\""
value is 10
Scenario 2
% proc x {} {
set c 10
uplevel {set val $c}
}
%
% proc y {} {
set c 10
uplevel "set val $c"
}
% x
can't read "c": no such variable
% y
10
% set val
10
%
In both of the scenarios, we can see that the variable substitution is performed on the body of the if loop (i.e. {puts "value is $a"}), whereas in the uplevel, it is not (i.e. {set val $c}), based on the current context.
I can see it as if like they might have access it via upvar kind of stuffs may be. But, why it has to be different among places ? Behind the scene, why it has to be designed in such this way ? Or is it just a conventional way how Tcl works?
Tcl always works exactly the same way with exactly one level of interpretation, though there are some cases where there is a second level because a command specifically requests it. The way it works is that stuff inside braces is never interpolated or checked for word boundaries (provided those braces start at the start of a “word”), stuff in double quotes is interpolated but not parsed for word boundaries (provided they start a word), and otherwise both interpolation and word boundary scanning are done (with the results of interpolation not scanned).
But some commands send the resulting word through again. For example:
eval {
puts "this is an example with your path: $env(PATH)"
}
The rule applies to the outer eval, but that concatenates its arguments and then sends the results into Tcl again. if does something similar with its body script except there's no concatenation, and instead there's conditional execution. proc also does the same, except it delays running the code until you call the procedure. The expr command is like eval, except that sends the script into the expression evaluation engine, which is really a separate little language. The if command also uses the expression engine (as do while and for). The expression language understands $var (and […]) as well.
So what happens if you do this?
set x [expr $x + $y]
Well, first we parse the first word out, set, then x, then with the third word we start a command substitution, which recursively enters the parser until the matching ] is found. With the inner expr, we first parse expr, then $x (reading the x variable), then +, then $y. Now the expr command is invoked with three arguments; it concatenates the values with spaces between them and sends the result of the concatenation into the expression engine. If you had x previously containing $ab and y containing [kaboom], the expression to evaluate will be actually:
$ab + [kaboom]
which will probably give you an error about a non-existing variable or command. On the other hand, if you did expr {$x + $y} with the braces, you'll get an addition applied to the contents of the two variables (still an error in this case, because neither looks like a number).
You're recommended to brace your expressions because then the expression that you write is the expression that will be evaluated. Otherwise, you can get all sorts of “unexpected” behaviours. Here's a mild example:
set x {12 + 34}
puts [expr $x]
set y {56 + 78}
puts [expr $y]
puts [expr $x * $y]
Remember, Tcl always works the same way. No special cases. Anything that looks like a special cases is just a command that implements a little language (often by calling recursively back into Tcl or the expression engine).
In addition to Donal Fellows's answer:
In scenario 2, in x the command uplevel {set val $c} is invoked, and fails because there is no such variable at the caller's level.
In y, the equivalent of uplevel {set val 10} is invoked (because the value of c is substituted when the command is interpreted). This script can be evaluated at the caller's level since it doesn't depend on any variables there. Instead, it creates the variable val at that level.
It has been designed this way because it gives the programmer more choices. If we want to avoid evaluation when a command is prepared for execution (knowing that the command we invoke may still evaluate our variables as it executes), we brace our arguments. If we want evaluation to happend during command preparation, we use double quotes (or no form of quoting).
Now try this:
% set c 30
30
% x
30
% y
10
If there is such a variable at the caller's level, x is a useful command for setting the variable val to the value of c, while y is a useful command for setting the variable val to the value encapsulated inside y.

While debugging, how can I jump to a function, execute it and return from where I left off?

Say function A consists of 10 lines. I set a breakpoint at line 5, when I hit it, I want to Execute function B, before returning to A. On return, Id like the flow to continue at line 5.
The lldb expr command evaluates a C/ObjC/C++ expression in the current program context, using user defined variables and variables currently in scope.
Examples:
expr -- functionB(17)
expr -- [self methodB]
Sometimes it is necessary to specify the return value explicitly, for example
expr -- (void)functionB(17)
If the function returns an Objective-C object then you can use po as an alias
for expression -O --, in that case lldb prints the description of the return value.
You can also add the debugger command as an "Action" to the breakpoint,
to have it executed automatically when the breakpoint is hit:

CMake: difference between ${} and "${}"

What is the difference, in cmake, between something like:
set(any_new_var ${old_var})
and
set(any_new_var "${old_var}")
Any important difference? When have I to use one or the other form?
For example, I try with the next mini test
# test.cmake
# Variable 'a' isn't defined.
set(hola "${a}")
# message(${hola})
message("${hola}")
The output of this mini-test (cmake -P test.cmake) is a empty line (because 'a' isn't defined). If I uncomment the first message, cmake throws an message error:
CMake Error at prueba.cmake:6 (message):
message called with incorrect number of arguments
Why in the second case it doesn't throw and error but an empty line?
In CMake strings can be interpreted as lists. The rule is simple: to form the list split the string at semicolons. For example, the string value one;two;three can be thought of as a list of three elements: one, two, and three.
To invoke a command you write the command name and some words between parentheses. However, these words do not correspond to the arguments the command receive in a one-to-one fashion. Each word become zero or more arguments, and all the arguments get concatenated together.
Unless a word is quoted, it is treated as a list and is expanded to multiple arguments. A quoted word always becomes a single argument.
For example, assume that X is bound to one;two;three, Y is bound to the empty string, and Z is bound to foo. The following command invocation has three words, but the command receives four arguments:
some_command(${X} ${Y} ${Z})
# The command receives four arguments:
# 1. one
# 2. two
# 3. three
# 4. foo
If we would have quoted the words, the command would have received three arguments:
some_command("${X}" "${Y}" "${Z}")
# The command receives three arguments:
# 1. one;two;three
# 2. (the empty list)
# 3. foo
To return to your original question: the message command can receive a varying number of arguments. It takes all its arguments, concatenates them together into one string, and then prints that string. For some unknown reason it does not accept zero arguments, though.
The behavior message has with multiple arguments is not very useful, so you tend to use a single quoted argument with it:
set(SOURCES foo.c hoo.h)
message(${SOURCES}) # prints foo.cfoo.h
message("${SOURCES}") # prints foo.c;foo.h
Also, when set receives multiple arguments it builds a string of the arguments separated by semicolons. The variable is then set to that string.