I'm trying to port code from DML 1.2 to DML 1.4. Here is part of code that i ported:
group rx_queue [i < NQUEUES] {
<...>
param desctype = i < 64 #? regs.SRRCTL12[i].DESCTYPE.val #: regs.SRRCTL2[i - 64].DESCTYPE.val; // error occurs here
<...>
}
Error says:
error: non-constant expression: cast(i, int64 ) < 64
How can i specify parameter dependent on index value?
I tried to use if...else instead ternary operator, but it says that conditional parameters are not allowed in DML.
Index parameters in DML are a slightly magical expressions; when used from within parameters, they can evaluate to either a constant or a variable depending on where the parameter is used from. Consider the following example:
group g[i < 5] {
param x = i * 4;
method m() {
log info: "%d", x;
log info: "%d", g[4 - i].x;
log info: "%d", g[2].x;
}
}
i becomes an implicit local variable within the m method, and in params, indices are a bit like implicit macro parameters. When the compiler encounters x in the first log statement, the param will expand to i * 4 right away. In the second log statement, the x param is taken from an object indexed with the expression 4 - i, so param expansion will instead insert (5 - i) * 4. In the third log statement, the x param is taken from a constant indexed object, so it expands to 2 * 4 which collapses into the constant 8.
Most uses of desctype will likely happen from contexts where indices are variable, and the #? expression requires a constant boolean as condition, so this will likely give an error as soon as anyone tries to use it.
I would normally advise you to switch from #? to ? in the definition of the desctype param, but that fails in this particular case: DMLC will report error: array index out of bounds on the i - 64 expression. This error is much more confusing, and happens because DMLC automatically evaluates every parameter once with all zero indices, to smoke out misspelled identifiers; this will include evaluation of SRRCTL2[i-64] which collapses into SRRCTL2[-64] which annoys DMLC.
This is arguably a compiler bug; DMLC should probably be more tolerant in this corner. (Note that even if we would remove the zero-indexed validation step from the compiler, your parameter would still give the same error message if it ever would be explicitly referenced with a constant index, like log info: "%d", rx_queue[0].desctype).
The reason why you didn't get an error in DML 1.2 is that DML 1.2 had a single ternary operator ? that unified 1.4's ? and #?; when evaluated with a constant condition the dead branch would be disregarded without checking for errors. This had some strange effects in other situations, but made your particular use case work.
My concrete advise would be to replace the param with a method; this makes all index variables unconditionally non-constant which avoids the problem:
method desctype() -> (uint64) {
return i < 64 ? regs.SRRCTL12[i].DESCTYPE.val : regs.SRRCTL2[i - 64].DESCTYPE.val;
}
In an Autohotkey script, once a user presses the CapsLock key, a SplashText should pop up indicating that it is ON, or out when it is OFF, the problem here is not about the code that gets it to work but how much simpler it can get.
There are different ways that do it, some need about 25 lines, some use SetTimer and GetKeyState internal functions and several loops to get it to run, some just about five and no loops.
Simplest:
#SingleInstance Force
SetCapsLockState, Off
~CapsLock::
If (Tog:=!Tog)
SplashTextOn ,350 ,35 , Wanted !, [CapsLock] Activated.
else
SplashTextOff
return
How does: If (Tog:=!Tog) get this code running so easily? Tog is just a variable not initiated, and each time the CapsLock is pressed it is continuously changing its value from 1 to 0
It seems to be acting as a Flag in the code? what am I missing in this line:
If (Tog:=!Tog)
What makes it evaluate different each time?
This is one below is another approach with A = 0 working as a switch, I made this one and it doesn't quite get as simple as I'd like it to be but it does the job.
Longer code:
#SingleInstance Force
SetCapsLockState, Off
~CapsLock::
If (A = 0)
{
SplashTextOn ,350 ,35 , Wanted !, [CapsLock] Activated.
A=1
}else
{
SplashTextOff
A=0
}
return
Longest code:
This last one gets the same result but checks the actual physical state of the key It wouldn't rely on SetCapsLockState, Off at the top of the script to make sure a switch will do the rest of the work in just one line as the simpler one.
#SingleInstance Force
#Persistent
SetTimer, StateCapsLockON_Timer, 100
Return
~CapsLock::
StateCapsLockON_Timer
If GetKeyState("CapsLock", "T")
{
SetTimer, StateCapsLockOFF_Timer, 100
SplashTextOn ,350 ,35 , Wanted !, [CapsLock] Activated.
SetTimer, StateCapsLockON_Timer, Off
}
Return
StateCapsLockOFF_Timer:
If !GetKeyState("CapsLock", "T")
{
SetTimer, StateCapsLockOFF_Timer, Off
SplashTextOff
SetTimer, StateCapsLockON_Timer, On
}
Return
Any good ideas about the way If (Tog:=!Tog) works in the simplest of these three examples?
I got this now, check logical-not on this link:
https://lexikos.github.io/v2/docs/Variables.htm
If the operand (In this case Tog) is blank or 0, the result of applying logical-not (or !Tog) is 1, which means "true". Otherwise, the result is 0 (false)
if (Tog = 0)
Tog = 1
would bring the same result as:
If Tog:=!Tog
Because an operation was taking place before the If even checked the changed value, if wasn't just comparing data, the operation was happening before the if since the values inside the parenthesis were not just being read but were also being changed and the variable being reassigned.
(expression) Any sub-expression enclosed in parentheses. For example, (3 + 2) * 2 forces 3 + 2 to be evaluated first.
The key difference is the usage of the assignment operator := as opposed to the comparing operator =. Since, as you've seen, you can evaluate expressions in an if-statement, you can actually include both operators in the same if-statement. Here's an example:
f1::
If (( test := 3+2 ) = 5 )
MsgBox
Return
Here "test" is first being assigned the sum of 3+2, then compared to 5. So, the key is that if-statements allow assignments to take place and that assignments take place first, that is, before anything is compared and evaluated to be true or false.
If there is no comparing operator (= , <, >, <=, >=), as is the case in your toggle, it just evaluates whether the variable itself is true or false. If the variable is blank, 0, or false, it evaluates to false; everything else is true, even the string "false".
Now for the fun bit. We can actually reduce your code to one line if we use Progress with the "zh0" option.
~CapsLock::Progress , % ( Tog := !Tog ) ? "zh0 w350 h35" : "Off" ,, [CapsLock] Activated. , Wanted !
Unfortunately, this isn't possible with SplashText since these are actually two separate commands. But the upside is that Progress actually has a lot more options available, so you can change the font size and color, etc.
Ok So i've got this Prolog code that represents an evolving world of blocks, and there's a robotic arm that can move 1 block at the time, and 2 little robots "rob and bor" that can paint blocks of their assigned color when the blocks are on top of a tower or on the bottom of a tower (See code for the conditions). function clear(X) is true when block X is on top of a tower, and ontable(X) is true when X is on the table (at the bottom of a tower). Single block towers return both clear and ontable as true.
The code aims to give all the solutions, step by step, when asked for a particular state (Like all 4 blocks on a single tower and red painted).
For that, there's a set of actions and facts defined, their conditioning effects (When action A is done under conditions C, what happens to the fact F) and a possibility/reality check with functions poss(returns true if some action is possible to do) and holds(returns true if some fact is true) that work on every state S. legal is the mix of these 2(Something is legal if everything in it holds and is possible).
%% Object Declaration (problem-specific)
block(B) :- member(B,[a,b,c,d]).
% colors available for rob and bor
color(rob,B) :- member(B,[blue]).
color(bor,B) :- member(B,[red]).
%% Initial Situation (problem-specific)
holds(F,s0) :- member(F,[on(a,b),on(b,c),ontable(c), ontable(d), clear(a), clear(d)]).
holds(color(B,white),s0) :- block(B).
%% Blocks World Preconditions (domain-specific)
%% action move_to_block(X,Z) moves block X on top of block Z
% poss is true when its possible to do the action.
poss(move_to_block(X,Z),S) :-
holds(clear(X),S), holds(clear(Z),S), Z\=X, \+ holds(on(X,Z),S).
poss(move_to_table(X),S) :-
holds(clear(X),S), \+ holds(ontable(X),S).
%% Robot R paints block B of color C
poss(paint(rob,B,C),S) :-
color(rob,C),holds(clear(B),S), \+ holds(color(B,C),S).
poss(paint(bor,B,C),S) :-
color(bor,C), holds(ontable(B),S), \+ holds(color(B,C),S).
%% Blocks World Effects (domain-specific)
% is_conditional_negative_effect(Act,Cond,Fact)
% when Act is peformed and Cond holds, Fact becomes false
is_conditional_negative_effect(move_to_block(X,_),on(X,Y),on(X,Y)).
is_conditional_negative_effect(move_to_block(X,_),ontable(X),ontable(X))
is_conditional_negative_effect(move_to_block(X,Z),true,clear(Z)).
is_conditional_negative_effect(move_to_table(X),on(X,_),on(X,_)).
is_conditional_negative_effect(paint(R,B,C),color(B,D),color(B,D)).
% is_conditional_positive_effect(Act,Cond,Fact)
% when Act is peformed and Cond holds, Fact becomes true
is_conditional_positive_effect(move_to_block(X,_),on(X,Y),clear(Y)).
is_conditional_positive_effect(move_to_block(X,Z),true ,on(X,Z)).
is_conditional_positive_effect(move_to_block(X,_),true,clear(X)).
is_conditional_positive_effect(move_to_table(X),true ,ontable(X)).
is_conditional_positive_effect(move_to_table(X),on(X,Y),clear(Y)).
is_conditional_positive_effect(move_to_table(X),true,clear(X)).
is_conditional_positive_effect(paint(R,B,C),color(B,_),color(B,C)).
holds(true,s0). % "true" always holds
holds(F,do(A,S)) :-
holds(F,S),
\+ (is_conditional_negative_effect(A,C,F), holds(C,S)).
holds(F,do(A,S)) :-
is_conditional_positive_effect(A,C,F),holds(C,S).
% S is legal if it is the result of performing executable actions
legal(s0).
legal(do(A,S)) :-
legal(S),
poss(A,S).
So thing is, when a consult done like follows ( time() only makes that the given answer returns the process time, for optimization sake... that's another problem i'll check later):
time((legal(S), holds(on(b,d),S), holds(on(c,b),S), holds(on(a,c),S), holds(color(b,blue),S), holds(color(a,red),S))).
SO far I get correct answers, but repeated like 10 times before it gives another, (correct too), so if I want all the answers, I've got to smash the ; like ten thousand times. I've been approximately 3 hours trying to solve this issue, since it doesn't let me check if I get all the correct answers or something is missing. Do you guys figure out what's going on?.
Tried to make everything as clear as possible, but comment if you need me to clarify something!
Finally, with a friend, we managed to fix it, the problem was on the positive conditional effects, specifically those related to clear. These affirmations were obvious, since a block must already return true to clear before being moved:
is_conditional_positive_effect(move_to_block(X,_),true,clear(X)).
is_conditional_positive_effect(move_to_table(X),true,clear(X)).
Also I changed some conditionals to be more specific, these greately improved the performance of the search:
is_conditional_negative_effect(move_to_table(X),on(X,_),on(X,_)).
was replaced by
is_conditional_negative_effect(move_to_table(X),on(X,Y),on(X,Y)).
and
is_conditional_positive_effect(paint(R,B,C),color(B,_),color(B,C)).
was replaced by
is_conditional_positive_effect(paint(R,B,C),true,color(B,C)).
Credits to my mate Pablo.
Is there a way to introspect a variable to directly find out what subset it was declared with? Here I create a subset, but introspection points me to its base type:
> subset Prime of Int where .is-prime
(Prime)
> my Prime $x = 23
23
> $x.WHICH
Int|23
I know it has to store the information somewhere, because if I try to reassign a value that doesn't match the subset, it fails:
> $x = 24
Type check failed in assignment to $x; expected Prime but got Int (24)
in block <unit> at <unknown file> line 1
I tried searching through the code, but I quickly get down into files like container.c and perl6_ops.c where the C code makes my eyes glaze over. I thought that X::TypeCheck::Assignment might help (see core/Exception.pm), but it's not clear to me where the expected value comes from. (see also this commit)
I feel like I'm missing something obvious.
I can check that something matches a subset, but that doesn't tell me if it were declared with a particular subset:
> my Int $y = 43;
43
> $y ~~ Prime;
True
I'm using Rakudo Star 2017.01
Inspired by a Zoffix's use of subsets in a recent post.
The value that you stored in $x is an Int. It is acceptable to the container (which you typed to Prime) because Prime is a subtype of Int.
So what you're interested in, is not the value in the container, but the type of the container. To get at the container, Perl 6 has the .VAR method. And that has an .of method to get at the type:
$ 6 'subset Prime of Int where .is-prime; my Prime $x; dd $x.VAR.of'
Prime
after a lot of trial/error and the search function I am still somewhat clueless about an I-thought-simple-thing (as always, hrmpf):
I have a column in a data frame x$question and within that column, there is an expression 'A/V' every once in a while, and I simply want it to be changed to 'A / B'.
I tried a little here and there, and thought this should work:
x$question[agrep('A/V',x$question)]<-'A / B'
but I get the error:
In `[<-.factor`(`*tmp*`, agrep('A/V', :
invalid factor level, NAs generated
or I could do this
agrep('A/V','A / B', x$question).
But here I get the error:
Error in .amatch_bounds(max.distance) :
match distance components must be non-negative
Since I am quite out of ideas, I would be very thankful, if you had a suggestions, or maybe an even simpler way of replacing a string with another string.
Does this work?
gsub("A/V","A/B",x$question)
Example:
x<-c("A/V", "A/V", "A/V")
x<-gsub("A/V","A/B",x)
>x
[1] "A/B" "A/B" "A/B"
Note: You can use ifelse for that too.
> ifelse(x=="A/B","A/V",x)
[1] "A/V" "A/V" "A/V"