Return multiple values: Difference between revisions
Content added Content deleted
No edit summary |
|||
Line 1,881: | Line 1,881: | ||
s, d = addsub( 7, 5 ) |
s, d = addsub( 7, 5 ) |
||
print( s, d )</syntaxhighlight> |
print( s, d )</syntaxhighlight> |
||
=={{header|M2000 Interpreter}}== |
|||
Functions can be made in 5 ways: Normal, Lambda, Simple, Group which return value, Pointer to Group which return value. For every way we can return multiple values as tuple (in a mArray type of array). The (a,b)=funcA() is a way to define/assign values from tuple. So (a,b)=(1, 2) is the simple form. A return value from a function done using = as statement. This return isn't the last statement (isn't exit from function), so may we have multiple = as statements and the last one which we execute return the value. By default if we don't use the = statement based on function's suffix at name (at call) we get 0 or "". Functions can return any type of types. So the return type based on statement = (or the interpreter return 0 or "" based on name at call, where suffix $ means we return empty string, although later versions of language can return string/ make string variables without suffix $). |
|||
<lang M2000 Interpreter> |
|||
module Return_multiple_values{ |
|||
Print "Using a function" |
|||
function twovalues(x) { |
|||
="ok", x**2, x**3 |
|||
} |
|||
// this is a sugar syntax to apply a tuple (mArray type) to variables |
|||
// can be new variables or pre defined |
|||
// if they are predifined then overflow may happen |
|||
byte b |
|||
// object a=(,) // if a is an object we can't assign number |
|||
(s, a,b)=twovalues(3) // twovalues(30) raise overflow |
|||
Print a=9, b=27, s="ok" |
|||
c=twovalues(3) |
|||
// need to use val$() because val() on string type is like a Val("1233") |
|||
Print c#val$(0)="ok", c#val(1)=9, c#val(2)=27, type$(c)="mArray" |
|||
// we can pass by reference |
|||
callbyref(&twovalues()) |
|||
sub callbyref(&a()) |
|||
local a, b, s as string |
|||
(s, a,b)=a(3) |
|||
Print a=9, b=27, s="ok" |
|||
end sub |
|||
} |
|||
Return_multiple_values |
|||
// modules may change definitions like functions (but not subs and simple functions) |
|||
Module Return_multiple_values{ |
|||
// lambdas are first citizens, can be called as functions or used as variables/values |
|||
Print "Using lambda function" |
|||
twovalues=lambda (x) ->{ |
|||
="ok", x**2, x**3 |
|||
} |
|||
byte b |
|||
(s, a,b)=twovalues(3) // twovalues(30) raise overflow |
|||
Print a=9, b=27, s="ok" |
|||
c=twovalues(3) |
|||
Print c#val$(0)="ok", c#val(1)=9, c#val(2)=27, type$(c)="mArray" |
|||
callbyref(&twovalues()) |
|||
callbyValue(twovalues, 3) |
|||
sub callbyref(&a()) |
|||
local a, b, s as string |
|||
(s, a,b)=a(3) |
|||
Print a=9, b=27, s="ok" |
|||
end sub |
|||
sub callbyValue(g, v) |
|||
local a, b, s as string |
|||
(s, a,b)=g(v) |
|||
Print a=9, b=27, s="ok" |
|||
end sub |
|||
} |
|||
Return_multiple_values |
|||
module Return_multiple_values{ |
|||
Print "Using simple function (static)" |
|||
byte b |
|||
(s, a,b)=@twovalues(3) // twovalues(30) raise overflow |
|||
Print a=9, b=27, s="ok" |
|||
c=@twovalues(3) |
|||
Print c#val$(0)="ok", c#val(1)=9, c#val(2)=27, type$(c)="mArray" |
|||
function twovalues(x) |
|||
="ok", x**2, x**3 |
|||
end function |
|||
} |
|||
Return_multiple_values |
|||
module Return_multiple_values { |
|||
// a group may used as function too |
|||
// we can use fields to alter state |
|||
// we can't pass the object as function by reference |
|||
// but we can pass an object function |
|||
// group is a static object to this module |
|||
// in every call of this module, this object initialised |
|||
// when the group statement executed |
|||
// and destroyed at the end of execution without a call to remove destructor |
|||
Print "Using a group as a function with a field" |
|||
group twovalues { |
|||
rep$="ok" |
|||
function forRef(x) { |
|||
=.rep$, x**2, x**3 |
|||
} |
|||
value () { // ![] pass the stack of values to forRef function |
|||
if empty then =this: exit |
|||
=.forRef(![]) // or use =.rep$, x**2, x**3 and (x) at value |
|||
} |
|||
Set { |
|||
Error "no object change allowed" |
|||
} |
|||
} |
|||
byte b |
|||
// object a=(,) // if a is an object we can't assign number |
|||
(s, a,b)=twovalues(3) |
|||
Print a=9, b=27, s="ok" |
|||
twovalues.rep$="Yes" |
|||
c=twovalues(3) |
|||
// need to use val$() because val() on string type is like a Val("1233") |
|||
Print c#val$(0)="Yes", c#val(1)=9, c#val(2)=27, type$(c)="mArray" |
|||
callbyref(&twovalues.forRef()) |
|||
callbyValue(twovalues, 3) |
|||
sub callbyref(&a()) |
|||
local a, b, s as string |
|||
(s, a,b)=a(3) |
|||
Print a=9, b=27, s="Yes" |
|||
end sub |
|||
sub callbyValue(g, v) |
|||
local a, b, s as string |
|||
(s, a,b)=g(v) |
|||
Print a=9, b=27, s="Yes" |
|||
end sub |
|||
} |
|||
Return_multiple_values |
|||
module Return_multiple_values { |
|||
Print "Using a pointer to group as a function with a field (group created by a Class)" |
|||
class iTwovalues { |
|||
string rep |
|||
function forRef(x) { |
|||
=.rep, x**2, x**3 |
|||
} |
|||
value () { // ![] pass the stack of values to forRef function |
|||
=.forRef(![]) |
|||
} |
|||
Set { |
|||
Error "no object change allowed" |
|||
} |
|||
// optional here, only to return the destriyed event (after the module exit from execution) |
|||
remove { |
|||
print .rep+" destroyed" |
|||
} |
|||
class: |
|||
Module iTwovalues (.rep) { |
|||
} |
|||
} |
|||
byte b |
|||
// twovalues is a pointer to an object of general type Group |
|||
twovalues->iTwovalues("ok") |
|||
Print twovalues is type iTwovalues = true |
|||
(s, a,b)=Eval(twovalues, 3) |
|||
Print a=9, b=27, s="ok" |
|||
twovalues=>rep="Yes" |
|||
c=twovalues=>forRef(3) // better to call a function instead of use Eval() |
|||
Print c#val$(0)="Yes", c#val(1)=9, c#val(2)=27, type$(c)="mArray" |
|||
for twovalues { |
|||
// we have to use for object { } to use references to members of object |
|||
callbyref(&.forRef()) |
|||
} |
|||
// if we hide the next statement we will see Yes destroyed after return from this module (before "done") |
|||
twovalues=pointer() // because twovalues is the last pointer to object, the object destroyed |
|||
// we see now: Yes destroyed |
|||
sub callbyref(&a()) |
|||
local a, b, s as string |
|||
(s, a,b)=a(3) |
|||
Print a=9, b=27, s="Yes" |
|||
end sub |
|||
} |
|||
Return_multiple_values |
|||
Print "Done" |
|||
</lang> |
|||
=={{header|Maple}}== |
=={{header|Maple}}== |