Argument in fuction call inside function definition is not being replaced in Maxima - arguments

The problem
Consider the following script written in Maxima
$ cat main.max
foo(a) ::= block(
if a = 0 then return(0) else return(1)
)$
bar(a) ::= block(
return(foo(a))
)$
foo(0);
bar(0);
Executing this script yields to
$ cat main.max | maxima --very-quiet
0
1
The question
Isn't it supposed that calling foo by itself results the same as if it is called from another function (in this scenario, bar)?
Here there is another example
$ cat main.max
foo(a) ::= block(disp(a))$
bar(a) ::= block(foo(a))$
foo(0)$
bar(0)$
$ cat main.max | maxima --very-quiet
0
a
In other words: Why isn't maxima replacing the argument that is passed to bar in the foo function call which is located within bar?
Additional context
This is the version that I'm currently using
$ maxima --version
Maxima 5.43.2

::= defines a function which quotes (does not evaluate) its arguments, and the return value of the function is evaluated by the caller. Such a function is conventionally called a "macro" for historical reasons.
I think you want an ordinary, argument-evaluating function, which is defined by :=. Try substituting := for ::= in your function definitions -- when I try that, I get 0 for bar(0) as expected.
Macros are useful, but in relatively narrow circumstances. I think ordinary functions are much more common than macros.
As an aside, in the functions which you have shown, block and return are unneeded. My advice is to just leave them out and make the functions more succinct and therefore more clear. E.g.
foo(a) := if a = 0 then 0 else 1;
bar(a) := foo(a);
Finally, note that = is only literal comparison, not equivalence; equivalence is tested with equal. E.g. suppose x is not otherwise defined. Then is(x = 0) yields false, but is(equal(x, 0)) yields the expression equal(x, 0). Depending on what you're doing, one or the other might be appropriate.

Related

'==' type and pattern matching - wait for the other recursive calls and do nothing on a case

I have two questions concerning OCaml.
Firstly, what does the == means when defining a type.
For example you can see at the end of this page the following code:
type compteur == int;;
Then what is the difference with:
type compteur = int;;
Moreover I have an other question concerning pattern matching.
How to say that you want to return nothing on a case.
For example let's say I have a function f that returns a boolean:
let rec f v = function
| t when t<v -> true
| t when t > v -> f (t-1)
| t when t = v -> (* here a code to say that you do nothing, and wait for the other recursive call *)
type compteur == int is a syntax error. The only valid way to define a type alias is with =, not ==. It's just a typo on the page you linked.
How to say that you want to return nothing on a case.
The only way to return nothing from a function would be to exit the program, raise an exception or loop (or recur) infinitely. Otherwise a function always returns a value.
here a code to say that you do nothing, and wait for the other recursive call
What other recursive call? In the case that t = v only the code for that case will run. There is no other code to wait on.

For loops LUA Different Types

I wanted to learn more about for loops, as far as I know there are different types?
For instance,
for i = 1, 5 do
print("hello")
end
^ I know about this one, it's going to print hello 5 times, but there are others like the one below which I do not understand, specifically the index bit (does that mean it is number 1?) and what is the ipairs for
for index, 5 in ipairs(x) do
print("hello")
end
If there are any other types please let me know, I want to learn all of them and if you can provide any further reading I'd be more than greatful to check them out
As you can read in the Lua reference manual
3.3.5 For Statement
The for statement has two forms: one numerical and one generic.
The numerical for loop repeats a block of code while a control
variable runs through an arithmetic progression. It has the following
syntax:
stat ::= for Name ‘=’ exp ‘,’ exp [‘,’ exp] do block end
Example:
for i = 1, 3 do
print(i)
end
Will output
1
2
3
You seem familiar with that one. Read the reference manual section for more details.
The generic for statement works over functions, called iterators. On
each iteration, the iterator function is called to produce a new
value, stopping when this new value is nil. The generic for loop has
the following syntax:
stat ::= for namelist in explist do block end namelist ::= Name {‘,’
Name}
Example:
local myTable = {"a", "b", "c"}
for i, v in ipairs(myTable) do
print(i, v)
end
Will ouput
1 a
2 b
3 c
ipairs is one of those iterator functions mentioned:
Returns three values (an iterator function, the table t, and 0) so
that the construction
for i,v in ipairs(t) do body end will iterate over the key–value pairs (1,t[1]), (2,t[2]), ..., up to the first nil value.
Read more about ipairs and pairs here:
https://www.lua.org/manual/5.3/manual.html#pdf-pairs
https://www.lua.org/manual/5.3/manual.html#pdf-ipairs
Of course you can implement your own iterator functions!
Make sure you also read:
Programming in Lua: 7 Iterators and the Generic for
Yes, It will print hello 5 times
According to this answer on Difference between pairs, ipairs, and next?
ipairs does the exact same thing as pairs, but with a slight twist to it.
ipairs runs through the table, until it finds a nil value, or a value that is non-existent, if that makes sense. So, if you ran the script I showed you for pairs, but just replaced pairs with ipairs, it would do the exact same thing

Is it possible to pass parameters by reference in Rebol?

Here, I have attempted to set the value of a global variable from inside a function, but the value has not changed:
setGlobalScope: func [theVar1] [
theVar1: 10
]
theVar: 1
setGlobalScope theVar
print theVar
"This prints 1 instead of 10. The value of theVar has not changed."
Is it possible to modify the value of a function's parameter from inside the function itself, so that the value is modified within the global scope instead of the function's scope?
You passed an integer value, not a word. Within the function, the word theVar1 is assigned the value of that integer. Reassigning it doesn't change it, because values like integers and dates and decimal numbers aren't "pointers" under the hood.
Hence, the answer from #sqlab where you can get around this by various ways of getting the word itself. The difference between function ['x] [code] and function [:x] [code] may interest you as an aside...
Why doesn't Rebol 3 honor quoted function parameters that are parenthesized?
But note that series values in Rebol do have modifying functions that affect the target, vs. just reassignment of where the word points. Consider:
setGlobalScope: func [theVar1 [string!]] [
clear theVar1
insert theVar1 "Modification"
]
theVar: "Original"
setGlobalScope theVar
print theVar
That prints Modification.
If you need to pass non-series values by reference, you need to put them in a series and use series modification operations instead of assignment. Because an assignment would just overwrite the "pointer" you have to the block or whatever. Worst case scenario you can wrap a single value in a block--if you must. But Rebol has a lot of "wait, look at it this other way..." where dialecting comes to the rescue in creating a better interface than that thing you were trying to clone from another less cool language. :-)
Mitigating the complexity of passing by reference is Rebol's simplicity at handling multiple return results:
foo: function [value1 value2] [
return reduce [
value1 + 7
value2 + 16
]
]
set [a b] foo 03 04
print a
print b
That outputs 10 and 20.
By using a combination of lit-word and get-word there is more than one way.
e.g
>> setGlobalScope: func ['theVar1] [set :theVar1 10]
>> theVar: 1
== 1
>>
>> setGlobalScope theVar
== 10
>>
>> print theVar
10
and
>> setGlobalScope: func [theVar1] [set :theVar1 10]
>> theVar: 1
== 1
>> setGlobalScope 'theVar
== 10
>> print theVar
10
I think you can just modify your variable theVar directly in your setGlobalScope funct.

How do I make a function use the altered version of a list in Mathematica?

I want to make a list with its elements representing the logic map given by
x_{n+1} = a*x_n(1-x_n)
I tried the following code (which adds stuff manually instead of a For loop):
x0 = Input["Enter x0"]
a = Input["a"]
M = {x0}
L[n_] := If[n < 1, x0, a*M[[n]]*(1 - M[[n]])]
Print[L[1]]
Append[M, L[1]]
Print[M]
Append[M, L[2]]
Print[M]
The output is as follows:
0.3
2
{0.3}
0.42
{0.3,0.42}
{0.3}
Part::partw: Part 2 of {0.3`} does not exist. >>
Part::partw: Part 2 of {0.3`} does not exist. >>
{0.3, 2 (1 - {0.3}[[2]]) {0.3}[[2]]}
{0.3}
It seems that, when the function definition is being called in Append[M,L[2]], L[2] is calling M[[2]] in the older definition of M, which clearly does not exist.
How can I make L use the newer, bigger version of M?
After doing this I could use a For loop to generate the entire list up to a certain index.
P.S. I apologise for the poor formatting but I could find out how to make Latex code work here.
Other minor question: What are the allowed names for functions and lists? Are underscores allowed in names?
It looks to me as if you are trying to compute the result of
FixedPointList[a*#*(1-#)&, x0]
Note:
Building lists element-by-element, whether you use a loop or some other construct, is almost always a bad idea in Mathematica. To use the system productively you need to learn some of the basic functional constructs, of which FixedPointList is one.
I'm not providing any explanation of the function I've used, nor of the interpretation of symbols such as # and &. This is all covered in the documentation which explains matters better than I can and with which you ought to become familiar.
Mathematica allows alphanumeric (only) names and they must start with a letter. Of course, Mathematic recognises many Unicode characters other than the 26 letters in the English alphabet as alphabetic. By convention (only) intrinsic names start with an upper-case letter and your own with a lower-case.
The underscore is most definitely not allowed in Mathematica names, it has a specific and widely-used interpretation as a short form of the Blank symbol.
Oh, LaTeX formatting doesn't work hereabouts, but Mathematica code is plenty readable enough.
It seems that, when the function definition is being called in
Append[M,L2], L2 is calling M[2] in the older definition of M,
which clearly does not exist.
How can I make L use the newer, bigger version of M?
M is never getting updated here. Append does not modify the parameters you pass to it; it returns the concatenated value of the arrays.
So, the following code:
A={1,2,3}
B=Append[A,5]
Will end up with B={1,2,3,5} and A={1,2,3}. A is not modfied.
To analyse your output,
0.3 // Output of x0 = Input["Enter x0"]. Note that the assignment operator returns the the assignment value.
2 // Output of a= Input["a"]
{0.3} // Output of M = {x0}
0.42 // Output of Print[L[1]]
{0.3,0.42} // Output of Append[M, L[1]]. This is the *return value*, not the new value of M
{0.3} // Output of Print[M]
Part::partw: Part 2 of {0.3`} does not exist. >> // M has only one element, so M[[2]] doesn't make sense
Part::partw: Part 2 of {0.3`} does not exist. >> // ditto
{0.3, 2 (1 - {0.3}[[2]]) {0.3}[[2]]} (* Output of Append[M, L[2]]. Again, *not* the new value of M *)
{0.3} // Output of Print[M]
The simple fix here is to use M=Append[M, L[1]].
To do it in a single for loop:
xn=x0;
For[i = 0, i < n, i++,
M = Append[M, xn];
xn = A*xn (1 - xn)
];
A faster method would be to use NestList[a*#*(1-#)&, x0,n] as a variation of the method mentioned by Mark above.
Here, the expression a*#*(1-#)& is basically an anonymous function (# is its parameter, the & is a shorthand for enclosing it in Function[]). The NestList method takes a function as one argument and recursively applies it starting with x0, for n iterations.
Other minor question: What are the allowed names for functions and lists? Are underscores allowed in names?
No underscores, they're used for pattern matching. Otherwise a variable can contain alphabets and special characters (like theta and all), but no characters that have a meaning in mathematica (parentheses/braces/brackets, the at symbol, the hash symbol, an ampersand, a period, arithmetic symbols, underscores, etc). They may contain a dollar sign but preferably not start with one (these are usually reserved for system variables and all, though you can define a variable starting with a dollar sign without breaking anything).

Ruby: Assign output of a function only if it does not return nil

When programming in Ruby I quite often have assignments like the following
test = some_function if some_function
With that assignments I want to assign the output of a function, but if it returns nil I want to keep the content of the variable. I know there are conditional assignments, but neither ||= nor &&= can be used here. The shortest way I found to describe the statement above is
test = (some_function or test)
Is there a better / shorter way to do this?
I don't think there's anything better than the last snippet you showed but note that or is used for flow control, use || instead:
test = some_function || test
It's usually better to assign new values to new names, the resulting code is easier to understand and debug since variables/symbols have the same value throughout the scope:
some_different_and_descriptive_name_here = some_function || test
I'd just add parentheses
(a = b) unless b.nil?
(a = b) if b
being inferior because if b is false then a remains as before
Keep in mind that this evaluates b twice, so if b is a function with side-effects (such as changing variables outside of its scope or printing) it will do that twice; to avoid this you must use
temp = b; (a = temp) unless temp.nil?
(which can, of course, be split into)
temp = b
(a = temp) unless temp.nil?

Resources