nvm, I just needed to define the variables to have a global scope
On Saturday, May 2, 2015 at 12:09:14 PM UTC-4, Edward Chen wrote:
>
> To follow up on this question, if I am using this eval(parse(foo))
> formalism within a wrapper function, it seems that if I define the input
> arguments for foo (a first-class function object) within this wrapper
> function that the arguments can't be found.
>
> example:
>
> function foo(arg)
>
> return arg+3
>
> end
>
> function wrapper(bar)
>
> arg = 3
>
> output = eval(parse("foo"))
>
> end
>
> then I get an error saying that the "arg" is not defined when I run:
>
> julia>> wrapper("foo")
>
> Much appreciated,
> Ed
>
> On Wednesday, May 8, 2013 at 12:44:58 PM UTC-4, Stefan Karpinski wrote:
>>
>> Excellent. Have fun! First-class metaprogramming is addictive.
>>
>>
>> On Wed, May 8, 2013 at 12:22 PM, Theodore Papamarkou <
>> [email protected]> wrote:
>>
>>> P.S. I also noted your comment on avoiding building up strings and then
>>> parsing them, I will alter my approach so as to work with expressions
>>> directly. Cheers!
>>>
>>>
>>> On Wednesday, May 8, 2013 5:19:25 PM UTC+1, Theodore Papamarkou wrote:
>>>>
>>>> Thank you very much Stefan, this is really helpful. I understood your
>>>> reply and educative comments, which by the way helped me get on with what
>>>> I
>>>> was doing. I wanted to access nested elements of an the args field of an
>>>> expression as part of the tree traversal I have been working on, and your
>>>> eval(parse()) suggestion resolved my problems:
>>>>
>>>> julia> tmp01 = :(x+3y)
>>>> :(+(x,*(3,y)))
>>>>
>>>> julia> eval(parse("tmp01.args[3].args[3]"))
>>>> :y
>>>>
>>>> I wasn't aware of the powerful parse() function. Thanks a lot!
>>>>
>>>> On Wednesday, May 8, 2013 5:05:02 PM UTC+1, Stefan Karpinski wrote:
>>>>>
>>>>> On Wed, May 8, 2013 at 11:15 AM, Theodore Papamarkou <
>>>>> [email protected]> wrote:
>>>>>
>>>>>> I'm trying to do sth that I'm not sure it's doable in Julia (and if
>>>>>> it is, I am not sure it is good Julia programming practice). Is it
>>>>>> possible
>>>>>> to parse and evaluate some code from an arbitrary string? For example,
>>>>>> if I
>>>>>> have the string "atype"*".args[2]"^2, is it possible somehow to evaluate
>>>>>> the corresponding code atype.args[2].args[2] in order to access the
>>>>>> nested
>>>>>> field of the atype array? Sth along the lines @eval
>>>>>> symbol("atype"*".args[2]"^2) or @eval $symbol("atype"*".args[2]"^2) is
>>>>>> apparently wrong coding.
>>>>>
>>>>>
>>>>> Yes, but unlike the "scripting languages" where the only way to
>>>>> generate and eval code is to build a string and then parse+evaluate it,
>>>>> Julia has a first-class representation of expressions, which are the
>>>>> preferred means of doing metaprogramming. You can, however, explicitly
>>>>> call
>>>>> the parse function to accomplish what you're talking about:
>>>>>
>>>>> julia> ex = parse("z = 2x + y^2 + 1")
>>>>> :(z = +(*(2,x),^(y,2),1))
>>>>>
>>>>>
>>>>> Of course, that just gives you a expression object and doesn't
>>>>> evaluate it. You need to call eval for that:
>>>>>
>>>>> julia> x,y = 2,3;
>>>>>
>>>>> julia> eval(ex)
>>>>> 14
>>>>>
>>>>>
>>>>> So the equivalent of eval(str) in Python (or Perl or Ruby) is
>>>>> eval(parse(str)) in Julia.
>>>>>
>>>>> <aside>
>>>>> When you write something like symbol("atype"*".args[2]"^2) you are
>>>>> creating a symbol with the very odd name "atype.args[2].args[2]", which
>>>>> is
>>>>> unlikely to be bound to anything when you evaluate it, although you could
>>>>> arrange for that to happen like this:
>>>>>
>>>>> julia> eval(:($(symbol("atype"*".args[2]"^2)) = 1))
>>>>> 1
>>>>>
>>>>> julia> eval(symbol("atype"*".args[2]"^2))
>>>>> 1
>>>>>
>>>>>
>>>>> </aside>
>>>>>
>>>>> In general, you're much better off manipulating Expr objects and
>>>>> Symbols than trying to build up strings for code and then parsing and
>>>>> evaluating them. It's much efficient, much more reliable, and you can do
>>>>> quite powerful, general transformations on expressions.
>>>>>
>>>>>
>>>>>> As side-questions (sorry to trouble you folks with several questions,
>>>>>> just getting to understand how to do metaprogramming in Julia):
>>>>>>
>>>>>
>>>>> No problem.
>>>>>
>>>>>
>>>>>> * is there a Julia function that takes an object as argument and
>>>>>> returns a string with the name of the object? As a continuation of the
>>>>>> above example, I am looking for a "name" function along the lines
>>>>>> name(atype) so as to get back the string "atype".
>>>>>>
>>>>>
>>>>> Objects don't have names, they're just values. Symbols have names and
>>>>> are bound to values, but many different names can be bound to the same
>>>>> value. You can sensibly say string(:atype) and you will get "atype" back,
>>>>> but you're asking for the string representation of the symbol :atype, not
>>>>> for the name of the value that atype refers to (it has no name).
>>>>>
>>>>> <aside>
>>>>> Then only exception to this is named functions, which do actually have
>>>>> a name:
>>>>>
>>>>> julia> f() = 1
>>>>> # methods for generic function f
>>>>> f() at none:1
>>>>>
>>>>> julia> g = f
>>>>> # methods for generic function f
>>>>> f() at none:1
>>>>>
>>>>>
>>>>> The function object still knows its original name was "f".
>>>>> </aside>
>>>>>
>>>>>
>>>>>> * I was looking at the function _jl_pre_exec in base/process.jl as a
>>>>>> means of understanding how Julia pointers work and noticed that C_NULL
>>>>>> is
>>>>>> the last element of ptrs... what does C_NULL do - why is it needed?
>>>>>>
>>>>>
>>>>> The execvp function
>>>>> <http://man7.org/linux/man-pages/man3/execvp.3.html> expects its
>>>>> second argument to be a NULL-terminated array of pointers to strings
>>>>> (which
>>>>> are themselves NULL-terminated arrays of bytes). The C_NULL has to be
>>>>> there
>>>>> so that execvp knows when it's done with the arguments to the program its
>>>>> going to exec.
>>>>>
>>>>
>>