Yes I realize now that I jumped the gun on my post. It would definitely be 
very useful if you could reduce this code


x = point.x
y = point.y
# do stuff on x and y
point.x = x
point.y = y


by something like

@fetch_and_store(Point, :foo, quote
   #do stuff on x and y
end)

p = Point(1, 0)
foo(p)


Where @fetch_and_store creates a function foo(point::Point) that handles 
all of the setup and storing of variables, but this still requires the type 
information of Point.  

On Monday, June 9, 2014 12:43:43 PM UTC-5, Jameson wrote:
>
> > something's probably wrong.
> Like this macro assuming you want to disable optimization of your code and 
> only work in the global scope without modules.
>
> I maintain my recommendation of using an immutable type (which allows llvm 
> to do some additional optimizations) and making a single local variable 
> with a shorter name for typing repeatedly. 
>
> The only feature somewhat unique to Visual Basic that I liked is the with 
> block , which is similar to what you are asking. I would love to have this 
> syntax in Julia too, but I'm not sure it is possible/a good idea. Since it 
> is just a source transform, it should avoid Stefan's note about the 
> compile/runtime distinction error. 
>
> On Monday, June 9, 2014, Stefan Karpinski <[email protected] 
> <javascript:>> wrote:
>
>> Any time there's an eval in what your macro emits, something's probably 
>> wrong. In this case, however, you can't really avoid it – largely because 
>> you can't do this correctly. The trouble is that the type of the object you 
>> want to bind the fields of is a runtime property, but you want to bind 
>> variables based on it – which is a compile-time property.
>>
>>
>> On Mon, Jun 9, 2014 at 12:55 PM, Nathaniel Nicandro <
>> [email protected]> wrote:
>>
>>> Oh, yes I see that now. Then what you could do is quote the call to 
>>> names() in your macro expression so the names call is executed in the 
>>> calling environment. 
>>>
>>> macro fetch(p)
>>>     return quote
>>>         local vars = names($p)
>>>         local ex = Expr(:block)
>>>         append!(ex.args, [:($v = $p.$v) for v in vars])
>>>         eval(ex)
>>>     end
>>> end
>>>
>>> This is similar to what yo have done at the REPL but it quotes the 
>>> names() call so it can get evaluated in the macro calling environment 
>>> instead of within the macro itself. ex =  Expr(:block) is just another 
>>> quote block with a list of expressions to evaluate in ex.args. Note that 
>>> there is no need to use esc() here because the eval() call happens in the 
>>> calling environment.
>>>
>>>
>>> On Monday, June 9, 2014 10:18:13 AM UTC-5, Andrew Simper wrote:
>>>>
>>>> Yes thanks for pointing that out, but if you look at this thread I 
>>>> already got some help with the |> esc for this type of thing over on 
>>>> another thread https://groups.google.com/forum/#!topic/julia-users/
>>>> UvBff9QVKaA , but I started this thread specifically to find out how 
>>>> to get write a macro using names(obj) to do the work instead of having to 
>>>> write a new fetch macro manually every time I create a new type. 
>>>>
>>>> On Monday, June 9, 2014 11:04:12 PM UTC+8, Nathaniel Nicandro wrote:
>>>>>
>>>>> You can use the esc 
>>>>> <http://julia.readthedocs.org/en/latest/stdlib/base/?highlight=esc#Base.esc>
>>>>>  function 
>>>>> that can introduce variables in the calling environment
>>>>>
>>>>> julia> type Point
>>>>>            x
>>>>>            y
>>>>>        end
>>>>>
>>>>> julia> macro fetch(p)
>>>>>            variables = quote
>>>>>                x = $p.x
>>>>>                y = $p.y
>>>>>            end
>>>>>            return esc(variables)
>>>>>        end
>>>>>
>>>>> julia> p = Point(5, 10)
>>>>> Point(5,10)
>>>>>
>>>>> julia> x
>>>>> ERROR: x not defined
>>>>>
>>>>> julia> y
>>>>> ERROR: y not defined
>>>>>
>>>>> julia> @fetch p;
>>>>>
>>>>> julia> x
>>>>> 5
>>>>>
>>>>> julia> y
>>>>> 10
>>>>>
>>>>>
>>>>>
>>>>> On Saturday, June 7, 2014 2:35:59 AM UTC-5, Andrew Simper wrote:
>>>>>>
>>>>>> A lot of the time it is good to copy a structure to local variables 
>>>>>> and then process on those for efficiency before storing the local values 
>>>>>> back to a structure. To help out with this I'm trying to write  a macro, 
>>>>>> so 
>>>>>> this is what I would like the end result to be:
>>>>>>
>>>>>> Point
>>>>>>     x::Float64
>>>>>>     y::Float64
>>>>>> end
>>>>>>
>>>>>> function process (p::Point)
>>>>>>     local x = p.x;
>>>>>>     local y = p.y;
>>>>>>     # do some processing on x and y
>>>>>>     p.x = x
>>>>>>     p.y = y
>>>>>> end
>>>>>>
>>>>>> and I would like write a macro that does this so the end code would 
>>>>>> like like:
>>>>>>
>>>>>> function process (p::Point)
>>>>>>     @fetch p
>>>>>>     # do some processing on x and y
>>>>>>     @store p
>>>>>> end
>>>>>>
>>>>>> So far I've got this working at the REPL using:
>>>>>>
>>>>>> point = Point (1, 2)
>>>>>> map (eval, ([:($name = point.$name) for name in names(point)]))
>>>>>> println("x=$(x) y=$(y)")
>>>>>>
>>>>>> which prints out: x=1.0 y=2.0
>>>>>>
>>>>>> Can someone please help out turning this into a macro?
>>>>>>
>>>>>>
>> 

Reply via email to