discuss@lists.openscad.org

OpenSCAD general discussion Mailing-list

View all threads

Variable behavior in for & if blocks

MF
mike.fraser.1945+osc@gmail.com
Thu, Sep 19, 2024 5:13 PM

As an OLD programmer, I am having trouble dealing with the strange behavior of variables inside for & ik blocks.

I’m basically trying to walk a list using the value at an index to calculate a cumulative value that specifies the location of an object.

I’m stuck. Please educate me as this behavior is foreign to Basic/Fortran/forth/perl/Python/java, etc

As an OLD programmer, I am having trouble dealing with the strange behavior of variables inside for & ik blocks. I’m basically trying to walk a list using the value at an index to calculate a cumulative value that specifies the location of an object. I’m stuck. Please educate me as this behavior is foreign to Basic/Fortran/forth/perl/Python/java, etc
TP
Torsten Paul
Thu, Sep 19, 2024 5:34 PM

Hi!

On 19.09.24 19:13, mike.fraser.1945+osc--- via Discuss wrote:

I’m basically trying to walk a list using the value at an index to
calculate a cumulative value that specifies the location of an object.

There are some examples for that specific case at:
https://en.wikibooks.org/wiki/OpenSCAD_User_Manual/Tips_and_Tricks

I’m stuck. Please educate me as this behavior is foreign to Basic/
Fortran/forth/perl/Python/java, etc

Comparable behavior can be found in hardware description languages
like VHDL and Verilog.

It's like one evaluation of the script represents one object at a
single point in time, so for a single evaluation variables can't have
different values at the same time. Like in math, where you assign
x = 3 and that will be the value for all x in the formula for
one calculation.

ciao,
Torsten.

Hi! On 19.09.24 19:13, mike.fraser.1945+osc--- via Discuss wrote: > I’m basically trying to walk a list using the value at an index to > calculate a cumulative value that specifies the location of an object. There are some examples for that specific case at: https://en.wikibooks.org/wiki/OpenSCAD_User_Manual/Tips_and_Tricks > I’m stuck. Please educate me as this behavior is foreign to Basic/ > Fortran/forth/perl/Python/java, etc Comparable behavior can be found in hardware description languages like VHDL and Verilog. It's like one evaluation of the script represents one object at a single point in time, so for a single evaluation variables can't have different values at the same time. Like in math, where you assign x = 3 and that will be the value for *all* x in the formula for one calculation. ciao, Torsten.
JG
Jonathan Gilbert
Thu, Sep 19, 2024 5:47 PM

Getting data into a for and if block is pretty straightforward, and mimics
behavior you're probably used to.

b = true;

if (b) {
echo("true");

}

yields:

Compiling design (CSG Tree generation)...

ECHO: "true"

And,

list = [0, 1, 2, 3, 4 ];
for (i = list) {
echo(i * 2);
}

yields:

Compiling design (CSG Tree generation)...
ECHO: 0
ECHO: 2
ECHO: 4
ECHO: 6
ECHO: 8

Getting data out of a for or if loop is a little trickier. To get the
result of a for loop, you have to treat it like a loop comprehension:

list = [0, 1, 2, 3, 4 ];

new_list = [for (i=list) i * 2];
echo(new_list);

Compiling design (CSG Tree generation)...

ECHO: [0, 2, 4, 6, 8]

Changing (well, setting, really, within a new scope) a value within an if
block is possible, but you can't get it out:

b = true;

echo("initially set as:", b);
if (b) {
echo("starts within the if() as:", b);
b = false;
echo("ends within the if() as:", b);
}
echo("final val:", b);

Compiling design (CSG Tree generation)...

ECHO: "initially set as:", true
ECHO: "starts within the if() as:", false
ECHO: "ends within the if() as:", false
ECHO: "final val:", true

To do so, you need to conditionally declare the value before you use it:

c = (true) ? "condition was true" : "condition was false";

echo(c);

Compiling design (CSG Tree generation)...

ECHO: "condition was true"

On Thu, Sep 19, 2024 at 10:26 AM mike.fraser.1945+osc--- via Discuss <
discuss@lists.openscad.org> wrote:

As an OLD programmer, I am having trouble dealing with the strange
behavior of variables inside for & ik blocks.

I’m basically trying to walk a list using the value at an index to
calculate a cumulative value that specifies the location of an object.

I’m stuck. Please educate me as this behavior is foreign to
Basic/Fortran/forth/perl/Python/java, etc


OpenSCAD mailing list
To unsubscribe send an email to discuss-leave@lists.openscad.org

Getting data into a for and if block is pretty straightforward, and mimics behavior you're probably used to. b = true; > if (b) { > echo("true"); > } yields: Compiling design (CSG Tree generation)... ECHO: "true" And, > list = [0, 1, 2, 3, 4 ]; > for (i = list) { > echo(i * 2); > } yields: > Compiling design (CSG Tree generation)... > ECHO: 0 > ECHO: 2 > ECHO: 4 > ECHO: 6 > ECHO: 8 Getting data *out* of a for or if loop is a little trickier. To get the result of a for loop, you have to treat it like a loop comprehension: list = [0, 1, 2, 3, 4 ]; > new_list = [for (i=list) i * 2]; > echo(new_list); Compiling design (CSG Tree generation)... > ECHO: [0, 2, 4, 6, 8] Changing (well, setting, really, within a new scope) a value within an if block is possible, but you can't get it out: b = true; > echo("initially set as:", b); > if (b) { > echo("starts within the if() as:", b); > b = false; > echo("ends within the if() as:", b); > } > echo("final val:", b); > Compiling design (CSG Tree generation)... > ECHO: "initially set as:", true > ECHO: "starts within the if() as:", false > ECHO: "ends within the if() as:", false > ECHO: "final val:", true To do so, you need to conditionally declare the value before you use it: c = (true) ? "condition was true" : "condition was false"; > echo(c); Compiling design (CSG Tree generation)... > ECHO: "condition was true" On Thu, Sep 19, 2024 at 10:26 AM mike.fraser.1945+osc--- via Discuss < discuss@lists.openscad.org> wrote: > As an OLD programmer, I am having trouble dealing with the strange > behavior of variables inside for & ik blocks. > > I’m basically trying to walk a list using the value at an index to > calculate a cumulative value that specifies the location of an object. > > I’m stuck. Please educate me as this behavior is foreign to > Basic/Fortran/forth/perl/Python/java, etc > _______________________________________________ > OpenSCAD mailing list > To unsubscribe send an email to discuss-leave@lists.openscad.org > -- - Jon Gilbert jong@jong.org / jgilbertsjc@gmail.com
FH
Father Horton
Thu, Sep 19, 2024 5:56 PM

Sometimes recursion is a better approach, depending on what you're trying
to do and how long the list of values could be.

vals = [1, 2, 3, 6, 8, 9];

function findit(target, sofar = 0, ptr = 0) =
target < sofar ? ptr : findit(target, sofar + vals[ptr], ptr + 1);

echo(findit(15));

On Thu, Sep 19, 2024 at 12:48 PM Jonathan Gilbert via Discuss <
discuss@lists.openscad.org> wrote:

Getting data into a for and if block is pretty straightforward, and mimics
behavior you're probably used to.

b = true;

if (b) {
echo("true");

}

yields:

Compiling design (CSG Tree generation)...

ECHO: "true"

And,

list = [0, 1, 2, 3, 4 ];
for (i = list) {
echo(i * 2);
}

yields:

Compiling design (CSG Tree generation)...
ECHO: 0
ECHO: 2
ECHO: 4
ECHO: 6
ECHO: 8

Getting data out of a for or if loop is a little trickier. To get the
result of a for loop, you have to treat it like a loop comprehension:

list = [0, 1, 2, 3, 4 ];

new_list = [for (i=list) i * 2];
echo(new_list);

Compiling design (CSG Tree generation)...

ECHO: [0, 2, 4, 6, 8]

Changing (well, setting, really, within a new scope) a value within an if
block is possible, but you can't get it out:

b = true;

echo("initially set as:", b);
if (b) {
echo("starts within the if() as:", b);
b = false;
echo("ends within the if() as:", b);
}
echo("final val:", b);

Compiling design (CSG Tree generation)...

ECHO: "initially set as:", true
ECHO: "starts within the if() as:", false
ECHO: "ends within the if() as:", false
ECHO: "final val:", true

To do so, you need to conditionally declare the value before you use it:

c = (true) ? "condition was true" : "condition was false";

echo(c);

Compiling design (CSG Tree generation)...

ECHO: "condition was true"

On Thu, Sep 19, 2024 at 10:26 AM mike.fraser.1945+osc--- via Discuss <
discuss@lists.openscad.org> wrote:

As an OLD programmer, I am having trouble dealing with the strange
behavior of variables inside for & ik blocks.

I’m basically trying to walk a list using the value at an index to
calculate a cumulative value that specifies the location of an object.

I’m stuck. Please educate me as this behavior is foreign to
Basic/Fortran/forth/perl/Python/java, etc


OpenSCAD mailing list
To unsubscribe send an email to discuss-leave@lists.openscad.org

--


OpenSCAD mailing list
To unsubscribe send an email to discuss-leave@lists.openscad.org

Sometimes recursion is a better approach, depending on what you're trying to do and how long the list of values could be. vals = [1, 2, 3, 6, 8, 9]; function findit(target, sofar = 0, ptr = 0) = target < sofar ? ptr : findit(target, sofar + vals[ptr], ptr + 1); echo(findit(15)); On Thu, Sep 19, 2024 at 12:48 PM Jonathan Gilbert via Discuss < discuss@lists.openscad.org> wrote: > Getting data into a for and if block is pretty straightforward, and mimics > behavior you're probably used to. > > b = true; >> if (b) { >> echo("true"); >> > } > > > yields: > > Compiling design (CSG Tree generation)... > > ECHO: "true" > > > And, > >> list = [0, 1, 2, 3, 4 ]; >> for (i = list) { >> echo(i * 2); >> } > > > yields: > >> Compiling design (CSG Tree generation)... >> ECHO: 0 >> ECHO: 2 >> ECHO: 4 >> ECHO: 6 >> ECHO: 8 > > > > Getting data *out* of a for or if loop is a little trickier. To get the > result of a for loop, you have to treat it like a loop comprehension: > > list = [0, 1, 2, 3, 4 ]; >> new_list = [for (i=list) i * 2]; >> echo(new_list); > > > Compiling design (CSG Tree generation)... >> ECHO: [0, 2, 4, 6, 8] > > > Changing (well, setting, really, within a new scope) a value within an if > block is possible, but you can't get it out: > > b = true; >> echo("initially set as:", b); >> if (b) { >> echo("starts within the if() as:", b); >> b = false; >> echo("ends within the if() as:", b); >> } >> echo("final val:", b); >> > > Compiling design (CSG Tree generation)... >> ECHO: "initially set as:", true >> ECHO: "starts within the if() as:", false >> ECHO: "ends within the if() as:", false >> ECHO: "final val:", true > > > To do so, you need to conditionally declare the value before you use it: > > c = (true) ? "condition was true" : "condition was false"; >> echo(c); > > > Compiling design (CSG Tree generation)... >> ECHO: "condition was true" > > > > > On Thu, Sep 19, 2024 at 10:26 AM mike.fraser.1945+osc--- via Discuss < > discuss@lists.openscad.org> wrote: > >> As an OLD programmer, I am having trouble dealing with the strange >> behavior of variables inside for & ik blocks. >> >> I’m basically trying to walk a list using the value at an index to >> calculate a cumulative value that specifies the location of an object. >> >> I’m stuck. Please educate me as this behavior is foreign to >> Basic/Fortran/forth/perl/Python/java, etc >> _______________________________________________ >> OpenSCAD mailing list >> To unsubscribe send an email to discuss-leave@lists.openscad.org >> > > > -- > - Jon Gilbert > jong@jong.org / jgilbertsjc@gmail.com > _______________________________________________ > OpenSCAD mailing list > To unsubscribe send an email to discuss-leave@lists.openscad.org >
AM
Adrian Mariano
Thu, Sep 19, 2024 8:39 PM

If you want the data in one iteration of a loop to depend on prior
iterations you have only two options:  recursion or C-style list
comprehension.  Generally I find recursion to be a little easier to use,
but the C-style list comprehension runs faster.  Recursion can also be
depth limited (and even slower) if you don't achieve tail recursion.

Here's an example from the BOSL2 library of how to implement a cumulative
sum using a C-style list comprehension.  Each iteration has its own scope
that behaves like a subscope of the previous one, so you can therefore make
what look like variable redefinitions.

function cumsum(v) =
v==[] ? [] :
//assert(is_consistent(v), "The input is not consistent." )
[for (a = v[0],
i = 1
;
i <= len(v)
;
a = i<len(v) ? a+v[i] : a,
i = i+1)
a];

On Thu, Sep 19, 2024 at 1:57 PM Father Horton via Discuss <
discuss@lists.openscad.org> wrote:

Sometimes recursion is a better approach, depending on what you're trying
to do and how long the list of values could be.

vals = [1, 2, 3, 6, 8, 9];

function findit(target, sofar = 0, ptr = 0) =
target < sofar ? ptr : findit(target, sofar + vals[ptr], ptr + 1);

echo(findit(15));

On Thu, Sep 19, 2024 at 12:48 PM Jonathan Gilbert via Discuss <
discuss@lists.openscad.org> wrote:

Getting data into a for and if block is pretty straightforward, and
mimics behavior you're probably used to.

b = true;

if (b) {
echo("true");

}

yields:

Compiling design (CSG Tree generation)...

ECHO: "true"

And,

list = [0, 1, 2, 3, 4 ];
for (i = list) {
echo(i * 2);
}

yields:

Compiling design (CSG Tree generation)...
ECHO: 0
ECHO: 2
ECHO: 4
ECHO: 6
ECHO: 8

Getting data out of a for or if loop is a little trickier. To get the
result of a for loop, you have to treat it like a loop comprehension:

list = [0, 1, 2, 3, 4 ];

new_list = [for (i=list) i * 2];
echo(new_list);

Compiling design (CSG Tree generation)...

ECHO: [0, 2, 4, 6, 8]

Changing (well, setting, really, within a new scope) a value within an if
block is possible, but you can't get it out:

b = true;

echo("initially set as:", b);
if (b) {
echo("starts within the if() as:", b);
b = false;
echo("ends within the if() as:", b);
}
echo("final val:", b);

Compiling design (CSG Tree generation)...

ECHO: "initially set as:", true
ECHO: "starts within the if() as:", false
ECHO: "ends within the if() as:", false
ECHO: "final val:", true

To do so, you need to conditionally declare the value before you use it:

c = (true) ? "condition was true" : "condition was false";

echo(c);

Compiling design (CSG Tree generation)...

ECHO: "condition was true"

On Thu, Sep 19, 2024 at 10:26 AM mike.fraser.1945+osc--- via Discuss <
discuss@lists.openscad.org> wrote:

As an OLD programmer, I am having trouble dealing with the strange
behavior of variables inside for & ik blocks.

I’m basically trying to walk a list using the value at an index to
calculate a cumulative value that specifies the location of an object.

I’m stuck. Please educate me as this behavior is foreign to
Basic/Fortran/forth/perl/Python/java, etc


OpenSCAD mailing list
To unsubscribe send an email to discuss-leave@lists.openscad.org

--


OpenSCAD mailing list
To unsubscribe send an email to discuss-leave@lists.openscad.org


OpenSCAD mailing list
To unsubscribe send an email to discuss-leave@lists.openscad.org

If you want the data in one iteration of a loop to depend on prior iterations you have only two options: recursion or C-style list comprehension. Generally I find recursion to be a little easier to use, but the C-style list comprehension runs faster. Recursion can also be depth limited (and even slower) if you don't achieve tail recursion. Here's an example from the BOSL2 library of how to implement a cumulative sum using a C-style list comprehension. Each iteration has its own scope that behaves like a subscope of the previous one, so you can therefore make what look like variable redefinitions. function cumsum(v) = v==[] ? [] : //assert(is_consistent(v), "The input is not consistent." ) [for (a = v[0], i = 1 ; i <= len(v) ; a = i<len(v) ? a+v[i] : a, i = i+1) a]; On Thu, Sep 19, 2024 at 1:57 PM Father Horton via Discuss < discuss@lists.openscad.org> wrote: > Sometimes recursion is a better approach, depending on what you're trying > to do and how long the list of values could be. > > vals = [1, 2, 3, 6, 8, 9]; > > function findit(target, sofar = 0, ptr = 0) = > target < sofar ? ptr : findit(target, sofar + vals[ptr], ptr + 1); > > echo(findit(15)); > > On Thu, Sep 19, 2024 at 12:48 PM Jonathan Gilbert via Discuss < > discuss@lists.openscad.org> wrote: > >> Getting data into a for and if block is pretty straightforward, and >> mimics behavior you're probably used to. >> >> b = true; >>> if (b) { >>> echo("true"); >>> >> } >> >> >> yields: >> >> Compiling design (CSG Tree generation)... >> >> ECHO: "true" >> >> >> And, >> >>> list = [0, 1, 2, 3, 4 ]; >>> for (i = list) { >>> echo(i * 2); >>> } >> >> >> yields: >> >>> Compiling design (CSG Tree generation)... >>> ECHO: 0 >>> ECHO: 2 >>> ECHO: 4 >>> ECHO: 6 >>> ECHO: 8 >> >> >> >> Getting data *out* of a for or if loop is a little trickier. To get the >> result of a for loop, you have to treat it like a loop comprehension: >> >> list = [0, 1, 2, 3, 4 ]; >>> new_list = [for (i=list) i * 2]; >>> echo(new_list); >> >> >> Compiling design (CSG Tree generation)... >>> ECHO: [0, 2, 4, 6, 8] >> >> >> Changing (well, setting, really, within a new scope) a value within an if >> block is possible, but you can't get it out: >> >> b = true; >>> echo("initially set as:", b); >>> if (b) { >>> echo("starts within the if() as:", b); >>> b = false; >>> echo("ends within the if() as:", b); >>> } >>> echo("final val:", b); >>> >> >> Compiling design (CSG Tree generation)... >>> ECHO: "initially set as:", true >>> ECHO: "starts within the if() as:", false >>> ECHO: "ends within the if() as:", false >>> ECHO: "final val:", true >> >> >> To do so, you need to conditionally declare the value before you use it: >> >> c = (true) ? "condition was true" : "condition was false"; >>> echo(c); >> >> >> Compiling design (CSG Tree generation)... >>> ECHO: "condition was true" >> >> >> >> >> On Thu, Sep 19, 2024 at 10:26 AM mike.fraser.1945+osc--- via Discuss < >> discuss@lists.openscad.org> wrote: >> >>> As an OLD programmer, I am having trouble dealing with the strange >>> behavior of variables inside for & ik blocks. >>> >>> I’m basically trying to walk a list using the value at an index to >>> calculate a cumulative value that specifies the location of an object. >>> >>> I’m stuck. Please educate me as this behavior is foreign to >>> Basic/Fortran/forth/perl/Python/java, etc >>> _______________________________________________ >>> OpenSCAD mailing list >>> To unsubscribe send an email to discuss-leave@lists.openscad.org >>> >> >> >> -- >> - Jon Gilbert >> jong@jong.org / jgilbertsjc@gmail.com >> _______________________________________________ >> OpenSCAD mailing list >> To unsubscribe send an email to discuss-leave@lists.openscad.org >> > _______________________________________________ > OpenSCAD mailing list > To unsubscribe send an email to discuss-leave@lists.openscad.org >