[julia-users] Re: Julia and Object-Oriented Programming

2015-10-24 Thread Abe Schneider
Swift has an interesting take on composition via protocols (note, it also 
has the concept of single inheritance):

https://developer.apple.com/library/ios/documentation/Swift/Conceptual/Swift_Programming_Language/Protocols.html

it avoids copying anything into the child class, but rather sets up both 
the variables and methods that a child class should support. How the 
variable is actually implemented in the class is up to the class (which I 
think is the nice part). Thus you can do:

protocol Foo {
  var x:Int { get set } // x must evaluate to an Int, and can be both 'get' 
and 'set'
}

class Bar: Foo {
  var x:Int // treat it as a simple Int
}

class Baz: Foo {
  var x_latent:Int

  // x is a 'functional' variable where we explicitly define how it is 
get'd and set'd
  var x:Int {
get {
  return x_latent/2
}
set {
  x_latent = 2*x
   }
}

While it does involve rewriting code (which I don't love), it importantly 
protects the developer from making mistakes (i.e. it will complain that `x` 
is not defined, and will force `x` to be of type Int).

Swift also has the concept of generics. You can make Protocols generic, so 
in theory you could make X of any type. Unfortunately, there appears to be 
a gap in the language (like Julia, it is still an evolving language), and 
making variables in the protocol appears to create issues down the line.


Re: [julia-users] Julia and Object-Oriented Programming

2015-10-23 Thread Abe Schneider
An OO approach is really just specifying an interface in a formal manner. 
The second you write any type of interface, you always risk making a choice 
that will haunt you down the road. I don't see the difference between:

class Foo {
  float getX() { ... }
  float getY() { ... }
}

and:

type Foo { ... }
function getX(f::Foo) -> float { ... }
function getY(f::Foo) -> float { ... }

except that an instance of `foo` is being passed implicitly in the first 
case. To that extent, I would say Julia OO (i.e. on the dispatching). Where 
it is not OO is in the layout of the data.

It is true that with a more OO language, because of its formalism, you run 
the risk of declaring variable types in a parent class that might not be 
correct in the child classes, so some planning is required. However, what 
you gain is better code in the long run. For example, I might have:

abstract Baz

type Foo <: Baz {
  x::Float
}

type Bar <: Baz {
  x::Float
}

and an interface:

getX{T <: Baz}(b::T) -> Float = b.x


which works fine, except maybe someone else comes along and writes:

type Blob <: Baz {
  myX::Float
}

Now to fix your interface, you have to write a separate `getX` for `Blob`. 
This might not seem like a big deal, except you might not catch this issue 
until run time (I don't think there is a way a static-checker could 
identify the problem). Imagine a large library or base of code, with many 
people working on the code, and you suddenly are exposed to a large number 
of issues.

This is why people advocate OOP. In the first definition of `Foo`, I know 
it will always have an `x`, and I can easily see the interface necessary to 
access it.

So, yes, an OO usually requires more work up-front. If Julia is meant to be 
purely scientific language which requires a code rewrite for real-world 
use, then I won't argue with not having a way to compose the data. However, 
in any project of medium to large complexity, it will make life much more 
difficult not having that capability.

On Thursday, October 22, 2015 at 4:00:36 PM UTC-4, vav...@uwaterloo.ca 
wrote:
>
> One way to build a code-base that everyone can share is to specify 
> interfaces to datatypes as in methods in C++ base classes.  Another way is 
> for each individual to write his/her own code, and then read everyone 
> else's code, and then meet at coffee shops and talk on the phone to get 
> things to work together.  I am claiming that the second way is better for 
> scientific software than the first way because scientific software is more 
> open-ended than, say, systems software.  I am claiming that specifying 
> interfaces from the outset can lead to prematurely locking in design 
> decisions, and that I have seen examples of this in the real world.  Keep 
> in mind that Julia is being touted as a suitable language for both the 
> initial and the later phases of scientific software development.
>
> In the event that Julia adds new OO or other interface-specifying 
> features, obviously it would be possible for a team to ignore them, at 
> least initially.  But I have also seen in previous projects that there is a 
> tendency for people (including me) to jump onto the fanciest possible 
> solution offered by the programming language to solve a software design 
> problem.
>
> -- Steve Vavasis
>
>
> On Thursday, October 22, 2015 at 12:02:21 PM UTC-4, g wrote:
>>
>> What is the other option here? It seemed like with the OO/Julia way you 
>> are complaining about you at least have working (but slow) code handling 
>> your new polynomial type. In a case where your new type doesn't work with 
>> "obtainCoefficient", it won't 
>> work with any of your other code either. You would just have no working 
>> code with your new polynomial type. How is that better?
>>
>> But the next week, someone asks whether you can handle polynomials 
>>> specified as p(x)=det(A-x*B), where A and B are n-by-n matrices.  For 
>>> polynomials in this format, "obtainCoefficient" is expensive and would not 
>>> be regarded as a simple "getter" operation.  If many people had already 
>>> written functions invoking the 'obtainCoefficient' method, then you would 
>>> be stuck.  You would retrospectively realize that the obtainCoefficient 
>>> member function was not a good idea.  This example is typical of open-ended 
>>> scientific software projects.
>>>



Re: [julia-users] Julia and Object-Oriented Programming

2015-10-23 Thread Abe Schneider
Ah, okay, that is different then. What's the advantage of creating a new 
method versus copying the fields? I would imagine there is a penalty with 
each deference you have to follow in order to make that work.


I'm not familiar with Scala, so sorry if I'm telling you something you 
> know, but in go the member variables and methods are not copied over. The 
> Unicycle struct in go does not itself have those fields, the fields of the 
> struct do. In other words, defining
>
> type Unicycle struct {
> Frame
> Wheel
> Seat
> } 
>
> Is exactly like declaring 
>
> type Unicycle struct {
>Frame Frame
>Wheel Wheel
>SeatSeat
> } 
>
> except that in the former case one can call unicycle.Cushiness() , and in 
> the latter one must call unicycle.Seat.Cushiness(). In particular, if you 
> swap out one Frame in the unicycle for a different Frame, the field values 
> change (the methods won't, since methods are with a type).
>


Re: [julia-users] Julia and Object-Oriented Programming

2015-10-22 Thread Abe Schneider
I think this is generally in-line with what I've been advocating for, and 
not that different from Scala's mix-ins:

trait Wheel {
  // ...
}

trait Frame {
  // ...
}

class Unicycle extends trait Wheel, Frame {
   // ...
}

is essentially doing the same thing (i.e. copying the member variables and 
methods over).

As Stefan mentioned, Go is not traditional OO. This "composition-based" 
> approach is part of Go's OO approach. In go, a type can have named fields 
> of different types (like most OO languages), but also has "embedding". For 
> example, if one declared
>
> type Unicycle struct {
> Wheel
> Frame
> Seat
> }
>
> then you could access the individual fields directly. So, if "u' is of 
> type Unicycle, then you could access/set u.Cushiness directly. Similarly, 
> if the embedded types had methods, i.e. frame.Color(), they can be called 
> directly through unicycle, u.Color(). This is similar to, but distinct 
> from, inheritance (the difference is that the Unicycle type doesn't 
> actually have these fields, just the ability to call them easily, which is 
> significant because of interfaces). In the case of clashes, the program 
> must specify which is meant, so if both Seat and Frame had a Color() 
> method, the user would have to specify u.Frame.Color vs. u.Seat.Color. In 
> Go, this is handled by the compiler, and would need to be handled somewhere 
> in the Julia runtime/REPL. It's a very nice paradigm, but would have to be 
> made to fit within the broader Julia context.
>
>
>
>

[julia-users] Re: Julia and Object-Oriented Programming

2015-10-20 Thread Abe Schneider
As for class composition, this is how Scala does it:

http://www.scala-lang.org/old/node/117

I've previously suggested introducing a `trait` label as to keep type and 
dispatch information separate. Thus you could do:

trait A
  x::Int64
  y::Int64
end

trait B
  z::Int64
end

type foo(A, B) <: bar
# ...
end


It would then be natural to hang interfaces on traits (thus, instead of 
assuming a variable exists, you could specify an interface applies to a 
trait)

# only classes that mix-in trait B can call this function
get_x{C <: B}(b::C) = b.x
get_y{C <: B}(b::C) = b.y


That's my $0.02. 

On Tuesday, October 20, 2015 at 2:42:37 PM UTC-4, ssarkaray...@gmail.com 
wrote:
>
> It is a suggestion.  There is no project.  If some of the experts agree on 
> such a combined language in this group, a combined grammar
> can be created and ScalaJulia functional language can be implemented 
> through a project.
>
> We need some exchange of ideas. Such a combined language has implication 
> for Spark, Hadoop, Mlib and many other things to be integrated
> faster with Julia.
>
> SS
>
>
> On Tuesday, October 20, 2015 at 4:40:23 AM UTC-7, Sisyphuss wrote:
>>
>> I'm sorry, but I didn't find the ScalaJulia project as you mentioned.
>>
>>
>> On Monday, October 19, 2015 at 7:39:04 PM UTC+2, ssarkaray...@gmail.com 
>> wrote:
>>>
>>> I am confident that a new OOP language *ScalaJulia *is possible 
>>> integrating syntax of both functional languages Scala and Julia.
>>> Thanks,
>>> SS
>>>
>>> On Sunday, October 18, 2015 at 5:41:58 AM UTC-7, Sisyphuss wrote:

 When I'm learning Julia, I am always thinking what is the correct way 
 to do OOP in this language. It seems to me that what I learned in C++ does 
 not apply in Julia.

 It took me long to realize that the equivalent of Class of C++ in Julia 
 is not Type, but Module. Module is the basic function unit in Julia.

 Thus, a Class in Julia is like
 module ClassName # class Name {
 using# include<> // should be outside
 import   # include<>
 export  function # public  function;
 var = 1  # private static var;
 end  # }
 This provides the same structure as C++.

 However, this design has two issues:
 1) The visit control is not as fine-grained as in C++, the 
 encapsulation is not strict;
 2) Variables at the top level of a module are global variables.

 These two points are closely correlated. If we let module have private 
 variables, then they are not too different from local variables, ans thus 
 can be type inferred.
 I think this is a natural way to do OOP with Julia.





Re: [julia-users] Re: Julia and Object-Oriented Programming

2015-10-19 Thread Abe Schneider
I think I agree with 90% of what you wrote. I also don't know if anyone is 
arguing about single or multiple dispatch. Also, while Java and Borland's 
Object Pascal claimed a strong OO paradigm, C++ does does not (if you read 
Bjarne's design guide, he felt strongly that both OOP and functional were 
important). I'll note too, Java has slowly been moving towards a 
multi-paradigm approach by including Lambdas in the latest version.

Two of the languages you list below, Swift and Scala, also mix OO and 
functional programming. While Scala has a huge push for functional 
programming, it also provides the necessary constructs to talk about 
inheritance of data (while it doesn't provide multi-inheritance, it does 
have mix-ins).

I really like Julia's multi-dispatch approach, and have made great use of 
it in my own libraries. I don't think there should be any reason that 
classes should have to "own" the methods. However, what it currently 
doesn't do, is provide a method to specify the relationship of data within 
types between each other. You stated in the past this is because you want 
to keep dispatch-type separate from representation type. However, I think 
that's actually one of the most important aspects of OOP. Yes, you can 
always write an interface that assumes that each type has variable X, but I 
would claim ultimately that creates less maintainable code (partially 
because of DRY and partially because it turns what should be a compile-time 
error into a run-time error).

On Sunday, October 18, 2015 at 11:28:20 PM UTC-4, Stefan Karpinski wrote:
>
> It's a highly debatable claim that single dispatch class-based OO leads to 
> better or more maintainable software designs. I grew up on these kinds of 
> languages – Object Pascal, C++, Ruby, Java. Despite the ongoing rhetoric 
> that this paradigm solves all sorts of program design problems, that's just 
> not what I've seen. I think this style of programming has failed to be the 
> panacea that it was promised to be. If it was really such a success, then 
> we wouldn't be seeing a fresh crop of promising new programming languages – 
> Julia, Rust, Go, Clojure, Scala, Elixir, Elm, Swift, etc. – not a single 
> one of which is a traditional class-based OO language. The message is 
> clear: we need more effective solutions. So far, Julia's multiple dispatch 
> approach seems to me far better at addressing program maintainability and 
> extensibility than classes ever were. Julia does still need a way of 
> talking about interfaces and protocols in the language itself, but that's 
> ongoing design problem, not a fundamental issue.
>
> On Mon, Oct 19, 2015 at 8:18 AM, Abe Schneider <abe.sc...@gmail.com 
> > wrote:
>
>>
>>
>> On Sunday, October 18, 2015 at 9:44:21 PM UTC-4, vav...@uwaterloo.ca 
>> wrote:
>>>
>>> Going a bit on a tangent, I claim that object-oriented programming, at 
>>> least as embodied in C++, is not really suitable for scientific computing 
>>> and in fact has led certain codes to go astray.
>>>
>>
>> C++ is purposefully a multi-paradigm language for this reason. C++11 
>> added a lot of features specifically for functional aspects of the language.
>>  
>>
>>>
>>> To give a simple example, suppose you are told to write a 'matrix' class 
>>> in C++ that contains all the usual operations.  You finish writing your 
>>> class, and a week later, you are told to derive 'symmetric matrices' as a 
>>> subclass of 'matrices'.  This is trouble!  Unless you wrote your original 
>>> matrix class in a very particular way, you will have a hard time writing a 
>>> symmetric matrix class that inherits from a matrix base class.  This is not 
>>> just a theoretical example; I saw someone try to do this (unsuccessfully) 
>>> in a code he had written.
>>>
>>
>>
>> Sure, you always have the option to write bad code, but that doesn't make 
>> a particular paradigm good or bad. I think Torch7 has a good example of 
>> using object oriented programming for scientific programming.
>>  
>>
>>>
>>> The problem with object-oriented programming is that you have make 
>>> design decisions when you write the base classes that lock you into a 
>>> certain path.  This path may not be compatible with the flexibility needed 
>>> for scientific software projects.
>>>
>>
>> I think that's true with any language. In Julia you still have to define 
>> an interface to access the variables. Yes, there are fewer mechanisms in 
>> place that restrict access, but that isn't always a good thing. You end up 
>> trading compile-time errors for run-time errors. I much rather deal with

Re: [julia-users] Re: Julia and Object-Oriented Programming

2015-10-19 Thread Abe Schneider
My main argument in this thread is that I wouldn't consider Julia "true OO" 
in the terms many other languages would define it,
but trying not to pass any real judgement of whether that is a good thing 
or not (I agree with Stefan that it's an interesting experiment, and the 
language is still a work in progress).

Julia supports the OO concept in hierarchy in dispatch-type, but not in 
data-type. Clearly there is benefit to providing some type of 
organizational framework, and a hierarchical has helped on the 
dispatch-front. I've heard two arguments on data-type hierarchy: (1) It's 
not needed, and doesn't help in any way, and (2) it's not clear how to 
implement it, so it hasn't been attempted yet.

I disagree with (1). and am strongly empathetic to (2).  I don't think that 
hierarchy is the only way to organize code, but that it is a good way to 
organize some of the code some of the time. You will find other cases where 
functional or aspect programming is a better fit. Thus, I think instead of 
prescribing the best methodology for developers, it's better to provide the 
tools that they can employ however they see fit.

On Monday, October 19, 2015 at 9:42:11 AM UTC-4, Tim Holy wrote:
>
> On Sunday, October 18, 2015 07:38:24 PM Abe Schneider wrote: 
> > > Julia isn’t object-oriented, and will probably never be. But that 
> doesn’t 
> > > make it less powerful :) 
> > 
> > Of course it doesn't make it less powerful, but it also doesn't alway 
> lead 
> > to nice code. The point of OOP isn't that it gets you more power, but it 
> > gives you more maintainable code. 
>
> From my personal experience, I'd say it's abundantly clear that "true OO" 
> (whatever that really means) is not more maintainable than julia's type 
> system 
> + multiple dispatch. OO is great, and something you study in school 
> because 
> it's been around a long time, but that doesn't mean that in 2015 it's 
> still 
> the best organizing principle for code. 
>
> --Tim 
>
>

Re: [julia-users] Re: Julia and Object-Oriented Programming

2015-10-19 Thread Abe Schneider


On Monday, October 19, 2015 at 12:17:16 PM UTC-4, Tom Breloff wrote:
>
> Here's an example where there would normally be a strict hierarchy in 
> classic OOP:  Square <: Rectangle <: Shape 
>
> But it actually makes much more sense in Julia (why have 2 fields for 
> Square??):
>

Unfortunately most of the classic examples are simplified to the point of 
not being informative. A previous example I gave was the NN design of 
Torch7, where each module has an `output` and a `grad_input` parameter. The 
forward/backward ops of each module is different, but it's important to 
have those common variables.
 

>
> Now I completely agree that ensuring a compile-time agreement of interface 
> is a valuable part of the language (but should ideally be optional).  
> People do see value in this, and it's an active design discussion.  (search 
> for "traits")
>

I did take a look at what the Traits people were doing. Unfortunately, at 
least last time I looked at it, it still seemed to require a lot of code 
copying.
 

>
> For composition vs inheritance, I completely agree that sometimes it's 
> nice to save code/typing when you have structures with a bunch of fields 
> that are mostly the same.  I'd argue you don't actually care about 
> inheritance, you just want composition but without the extra layer of 
> structure. 
>

I strongly agree with this. If you hide all direct access to variables and 
only allow access via an interface, you can define a type as  a composition 
of other types and a list of supported interfaces:

@compose C(protocol1, protocol2) <| (A, B)
  other::AbstractString
end


Above, a relatively simple macro can replace all the "Type..." with the 
> fields of the composed types, applying multiple inheritance of the 
> structures without the baggage required in classic OOP.  Then you can 
> compose your type from other types, but without having to write 
> "unicycle.wheel.radius"... you can just write "unicycle.radius".
>

I suggested such a macro awhile ago (maybe a year?), and it was met with 
disapproval. Not that that should stop anyone from writing it, but it was 
deemed un-Julian (at least my take on people's responses). I think this can 
be seen as a type of mix-in similar to what Ruby and Scala do.

 

>
> On Mon, Oct 19, 2015 at 11:32 AM, Abe Schneider <abe.sc...@gmail.com 
> > wrote:
>
>> I think I agree with 90% of what you wrote. I also don't know if anyone 
>> is arguing about single or multiple dispatch. Also, while Java and 
>> Borland's Object Pascal claimed a strong OO paradigm, C++ does does not (if 
>> you read Bjarne's design guide, he felt strongly that both OOP and 
>> functional were important). I'll note too, Java has slowly been moving 
>> towards a multi-paradigm approach by including Lambdas in the latest 
>> version.
>>
>> Two of the languages you list below, Swift and Scala, also mix OO and 
>> functional programming. While Scala has a huge push for functional 
>> programming, it also provides the necessary constructs to talk about 
>> inheritance of data (while it doesn't provide multi-inheritance, it does 
>> have mix-ins).
>>
>> I really like Julia's multi-dispatch approach, and have made great use of 
>> it in my own libraries. I don't think there should be any reason that 
>> classes should have to "own" the methods. However, what it currently 
>> doesn't do, is provide a method to specify the relationship of data within 
>> types between each other. You stated in the past this is because you want 
>> to keep dispatch-type separate from representation type. However, I think 
>> that's actually one of the most important aspects of OOP. Yes, you can 
>> always write an interface that assumes that each type has variable X, but I 
>> would claim ultimately that creates less maintainable code (partially 
>> because of DRY and partially because it turns what should be a compile-time 
>> error into a run-time error).
>>
>> On Sunday, October 18, 2015 at 11:28:20 PM UTC-4, Stefan Karpinski wrote:
>>>
>>> It's a highly debatable claim that single dispatch class-based OO leads 
>>> to better or more maintainable software designs. I grew up on these kinds 
>>> of languages – Object Pascal, C++, Ruby, Java. Despite the ongoing rhetoric 
>>> that this paradigm solves all sorts of program design problems, that's just 
>>> not what I've seen. I think this style of programming has failed to be the 
>>> panacea that it was promised to be. If it was really such a success, then 
>>> we wouldn't be seeing a fresh crop of promising new programming languages – 
>>> Julia, Rust, Go, Clojure, Sca

[julia-users] Re: Julia and Object-Oriented Programming

2015-10-18 Thread Abe Schneider

>
>
> But I agree with Tobias and Simon - there is very little reason to try to 
> make Julia more object-oriented. All the power you get from OO is still 
> there, but you might need to think a little differently to harness it. If 
> you have a concrete problem, along the lines of “this is how I’d do it in 
> OO, but I don’t know how to do it in Julia”, the community is usually 
> pretty good att figuring something out. A recent example was that someone 
> wanted man.eat(food) rather than eat(man, food). A little thinking 
> outside the box turned out the IMO superior solution - instead of changing 
> the language to make it read better, just change the verb: feed(man, food)
> .
>
> Julia isn’t object-oriented, and will probably never be. But that doesn’t 
> make it less powerful :)
>
>
Of course it doesn't make it less powerful, but it also doesn't alway lead 
to nice code. The point of OOP isn't that it gets you more power, but it 
gives you more maintainable code.


 

> On Sunday, October 18, 2015 at 8:32:06 PM UTC+2, Tobias Knopp wrote:
>
> Julia is fully object oriented. The core of OO is not to write a dot 
>> between an object and an associated function but that one has virtual 
>> functions. Multiple dispatch provides just that.
>>
>> Cheers
>>
>> Tobi
>>
>> Am Sonntag, 18. Oktober 2015 15:15:50 UTC+2 schrieb Simon Danisch:
>>>
>>> This design has at least 3 issues, since you can't have instances of a 
>>> module.
>>> In general:
>>> I personally would value the discussion of why Julia needs more OOP 
>>> constructs much more, If one can show that there are terrible flaws in 
>>> Julia's model which are swiftly solvable with OOP.
>>> My guess is, that the argument "I learned X and can't transfer it to 
>>> Julia, so Julia needs to change", can't really convince anyone to start 
>>> implementing something rather involved.
>>>
>>> There are a lot of comments on people trying to bring OOP to Julia, 
>>> which are best summarized by: give Julia's model a chance and don't stick 
>>> to OOP - it will pay off.
>>> And this kind of comment is pretty understandable in my opinion, since 
>>> Julia is quite a sophistaced language with plenty of constructs to avoid 
>>> OOP.
>>> I don't see much value in OOP and Julia's multiple dispatch is actually 
>>> one of the things that brought me here ( I exclusively worked with OOP 
>>> languages before).
>>> Besides the current flaws, I think it's a better model for numerical 
>>> computing, it yields concise code, easier maintenance and it's easier to 
>>> add feature to an existing code base than it is in OOP.
>>>
>>> I think Julia should move forward by not mimicking OOP further, but 
>>> instead improve the current model - there's lots to do already.
>>> Wasting time by chasing after features from other languages will make it 
>>> much harder to turn Julia into a well rounded, sound language. (this only 
>>> applies to feature that get chased without a concrete problem)
>>>
>>> Best,
>>> Simon
>>>
>>>
>>> Am Sonntag, 18. Oktober 2015 14:41:58 UTC+2 schrieb Sisyphuss:

 When I'm learning Julia, I am always thinking what is the correct way 
 to do OOP in this language. It seems to me that what I learned in C++ does 
 not apply in Julia.

 It took me long to realize that the equivalent of Class of C++ in Julia 
 is not Type, but Module. Module is the basic function unit in Julia.

 Thus, a Class in Julia is like
 module ClassName # class Name {
 using# include<> // should be outside
 import   # include<>
 export  function # public  function;
 var = 1  # private static var;
 end  # }
 This provides the same structure as C++.

 However, this design has two issues:
 1) The visit control is not as fine-grained as in C++, the 
 encapsulation is not strict;
 2) Variables at the top level of a module are global variables.

 These two points are closely correlated. If we let module have private 
 variables, then they are not too different from local variables, ans thus 
 can be type inferred.
 I think this is a natural way to do OOP with Julia.



 ​
>


[julia-users] Re: Julia and Object-Oriented Programming

2015-10-18 Thread Abe Schneider


On Sunday, October 18, 2015 at 9:44:21 PM UTC-4, vav...@uwaterloo.ca wrote:
>
> Going a bit on a tangent, I claim that object-oriented programming, at 
> least as embodied in C++, is not really suitable for scientific computing 
> and in fact has led certain codes to go astray.
>

C++ is purposefully a multi-paradigm language for this reason. C++11 added 
a lot of features specifically for functional aspects of the language.
 

>
> To give a simple example, suppose you are told to write a 'matrix' class 
> in C++ that contains all the usual operations.  You finish writing your 
> class, and a week later, you are told to derive 'symmetric matrices' as a 
> subclass of 'matrices'.  This is trouble!  Unless you wrote your original 
> matrix class in a very particular way, you will have a hard time writing a 
> symmetric matrix class that inherits from a matrix base class.  This is not 
> just a theoretical example; I saw someone try to do this (unsuccessfully) 
> in a code he had written.
>


Sure, you always have the option to write bad code, but that doesn't make a 
particular paradigm good or bad. I think Torch7 has a good example of using 
object oriented programming for scientific programming.
 

>
> The problem with object-oriented programming is that you have make design 
> decisions when you write the base classes that lock you into a certain 
> path.  This path may not be compatible with the flexibility needed for 
> scientific software projects.
>

I think that's true with any language. In Julia you still have to define an 
interface to access the variables. Yes, there are fewer mechanisms in place 
that restrict access, but that isn't always a good thing. You end up 
trading compile-time errors for run-time errors. I much rather deal with 
compiler-time errors.
 

>
> I for one am glad that the designers of Julia decided not to make Julia an 
> object-oriented language, at least not in the C++ sense of the term.
>
>
I think there is a lot to be gained from a multi-paradigm approach. Having 
a language that is scientific-code friendly is important, but so is 
integrating it into larger systems.
 

>
>
>
> On Sunday, October 18, 2015 at 8:41:58 AM UTC-4, Sisyphuss wrote:
>>
>> When I'm learning Julia, I am always thinking what is the correct way to 
>> do OOP in this language. It seems to me that what I learned in C++ does not 
>> apply in Julia.
>>
>> It took me long to realize that the equivalent of Class of C++ in Julia 
>> is not Type, but Module. Module is the basic function unit in Julia.
>>
>> Thus, a Class in Julia is like
>> module ClassName # class Name {
>> using# include<> // should be outside
>> import   # include<>
>> export  function # public  function;
>> var = 1  # private static var;
>> end  # }
>> This provides the same structure as C++.
>>
>> However, this design has two issues:
>> 1) The visit control is not as fine-grained as in C++, the encapsulation 
>> is not strict;
>> 2) Variables at the top level of a module are global variables.
>>
>> These two points are closely correlated. If we let module have private 
>> variables, then they are not too different from local variables, ans thus 
>> can be type inferred.
>> I think this is a natural way to do OOP with Julia.
>>
>>
>>
>>

[julia-users] Re: Julia and Object-Oriented Programming

2015-10-18 Thread Abe Schneider
I would say that the module is closest to a c++ namespace, which itself can 
be thought of as a static class. Note, however, that in both cases you 
can't really have separate instances.

Because of the desire to separate dispatch from type information, Julia 
doesn't really follow the OOP paradigm. You can have a hierarchy of 
abstract types, but abstract types contain no information besides their 
name and place in the hierarchy. Because of multi-dispatch, functions live 
outside of types (i.e., because you can dispatch on all parameters, usually 
no one type owns that function). Finally, you can build an interface to 
mimic an OOP design, but each concrete type still has to re-define the 
variables (which, is one of the biggest advantages of an OOP design). 

One of the really nice things about Julia is that you could in theory 
create a macro to simulate OOP in Julia:

@class foo <: a, b, c
# ...
end

where `@class` creates a new type `foo`, which pulls in the member 
variables of `a`, `b`, and `c` to simulate a mix-in design.

On Sunday, October 18, 2015 at 8:41:58 AM UTC-4, Sisyphuss wrote:
>
> When I'm learning Julia, I am always thinking what is the correct way to 
> do OOP in this language. It seems to me that what I learned in C++ does not 
> apply in Julia.
>
> It took me long to realize that the equivalent of Class of C++ in Julia is 
> not Type, but Module. Module is the basic function unit in Julia.
>
> Thus, a Class in Julia is like
> module ClassName # class Name {
> using# include<> // should be outside
> import   # include<>
> export  function # public  function;
> var = 1  # private static var;
> end  # }
> This provides the same structure as C++.
>
> However, this design has two issues:
> 1) The visit control is not as fine-grained as in C++, the encapsulation 
> is not strict;
> 2) Variables at the top level of a module are global variables.
>
> These two points are closely correlated. If we let module have private 
> variables, then they are not too different from local variables, ans thus 
> can be type inferred.
> I think this is a natural way to do OOP with Julia.
>
>
>
>

Re: [julia-users] Re: macros generating macros in modules

2015-04-05 Thread Abe Schneider
That's definitely an option, though it seems sub-optimal to me if it's 
possible to automate it from a user's perspective. It may be that it just 
isn't possible, but if so, is it because it's something the language 
doesn't currently support or does it go against the philosophy of the 
language?

Specifically, several possible methods could provide the necessary 
mechanism:

(1) Ability to get a function based on a signature and a namespace. Yes, 
you can get the names of functions in a namespace, but I don't see a way to 
convert that name to an actual function without an eval.

(2) Ability to create an call-expression with a namespace indicate to use 
the function from that namespace. For example: Expr(:call, :sym, 
:foobar_namespace, args). This means no additional lookup is required on 
the user's part.

(3) Allow macros to generate macros. This is already partially supported, 
though it's not clear if this is intentional or not. c++ has shown that 
template programming can be both useful and powerful (e.g. offloading 
computation to compile time rather than runtime).


All of these methods are general and not specific to the problem.


On Sunday, April 5, 2015 at 10:18:03 AM UTC-4, Toivo Henningsson wrote:

 If users should supply additional parsers (which parse sub-ASTs, right?) 
 then it's not really possible to hide all the metaprogramming machinery 
 from them anyway. So why not let the user create the macro, and just supply 
 functions that make writing the macro implementation as easy as possible?



Re: [julia-users] Re: macros generating macros in modules

2015-04-05 Thread Abe Schneider
I think if I just copy bits of the current code in it might be the easiest. 
I have the following macro:

macro grammar(name, definitions)
  parsers = [:+, :*, :?, :|, :-, :^, :list, :integer, :float]
  mapped_parsers = map_symbol_to_function(parsers)
  return parseGrammar(name, definitions, ParserData(mapped_parsers))
end


where parseGrammar goes through the definitions and converts them into 
actual code. Its output is an Expr tree. The key part here, is that per 
line, another function `parseDefinition` is recursively called. The 
simplified version of it is:


function parseDefinition(name::String, ex::Expr, pdata::ParserData)
  # ...

  # look up the symbol in the expression tree to get the function
  parser = get(pdata.parsers, ex.args[1], nothing)
  if parser !== nothing
# call function on the rest of the expression
rule = parser(name, pdata, ex.args[2:end])
  end
end

Thus, all the parsers listed above will be called appropriately if their 
symbol is encountered. This used to be a monolithic function, but it seemed 
a much better design to keep each parser as its own thing. The parsers 
themselves are not complex. Here's the definition of the or-rule:

function|(name::String, pdata::ParserData, args::Array)
  left = parseDefinition($(name)_1, args[1], pdata)
  right = parseDefinition($(name)_2, args[2], pdata)
  return OrRule(name, value)
end


The `map_symbol_to_function` thus traverses the original `parsers` list 
created and maps the symbol to this function.


So, all of this currently works (and is viewable to anyone who is 
interested to see the full versions on PEGParser's github).

The issue is that currently `parsers` is a fixed list. I'm trying to figure 
out how to let the users of the library add their own. For example, suppose 
and `integer` parser wasn't yet made. Someone could create their own:

function integer(name::String, pdata::ParserData, args::Array)
  return IntegerRule(name)
end

and then pass it into the macro somehow in so when `parseDefinition` is 
called, it will be used.

Originally, the macro was written to allow custom parsers to be passed in 
with the grammar definition:

@grammar foo [integer] begin
  start = list(integer, r,[ \t\n]*)
end

Thus, the `grammar` macro would just append whatever you listed to the 
`parsers` list. However, the mapping of symbols to functions will fail 
because of the namespace issue.

Maybe, as others have argued, that's okay, because I'm trying to do too 
much in a macro. That's fine, so the next logical conclusion is that I 
should just generate code that does the mapping.

Also fine. BUT, don't forget that this mapping is there to support the 
function of macro. Specifically, the `parsers` list is used in the 
`parseDefinition` function for transforming a grammar definition into code. 
Thus, that means I would need a macro that generates code for another 
macro, bringing us to the original question posed.

One possible way around this might be that the macro doesn't actually have 
to generate another macro (which I think is probably the more elegant 
solution), but rather you could generate variables which the second macro 
can use. For example:

@set_parsers(integer)
# creates a parsers = [...] list
@grammar foo begin
  # checks if `parsers` list exists, if not creates its own
end

However, this approach seems dangerous, as it introduces variables that the 
user is unaware of.


On Sunday, April 5, 2015 at 12:28:21 AM UTC-4, Patrick O'Leary wrote:

 Let me ask the question slightly differently. Without constraining 
 yourself to legal Julia syntax, what would you like to go in, and what do 
 you want to come out? I get the feeling there's a design here that doesn't 
 have this complexity--my intuition is that a generic function can be used 
 to drive this just fine (called within a macro to facilitate the final 
 splice.) But that's still hard to concretely suggest. 

 On Saturday, April 4, 2015 at 9:39:57 PM UTC-5, Abe Schneider wrote:

 I don't understand how what I'm trying to do falls outside the domain of 
 transforming code. My main goal is to take a user-defined grammar and 
 create relevant code.

 More to the point, I think the general ability to generate expressions 
 based on functions/namespaces is also solidly in the domain of transforms. 
 I can imagine plenty of use-cases for language-bindings, communication, etc.

 Yes, there are many simple macros one can create, which are useful, but 
 there exists many useful things one can do with macros that can get more 
 complex.

 A

 On Saturday, April 4, 2015 at 10:11:25 PM UTC-4, Jameson wrote:

 I think the underlying issue may be that you are trying to have the 
 macro do too much, when you should instead be just doing source-code 
 transforms and preprocessing. One such example of a great use of a macro is 
 simply:

 macro special_foo(syntax_tree)
 return quote
 special_foo( $(QuoteNode(syntax_tree) )
 end
 end


 On Sat, Apr 4, 2015 at 8:05 PM

[julia-users] macros generating macros in modules

2015-04-04 Thread Abe Schneider
I should start off, not entirely sure this is an okay thing to do with 
Julia. Suppose I want to create a macro that generates another macro, I can 
write:

macro meta_macro(x)
  quote
macro foo(y)
  $x+y
end
  end
end

and then call it and the generated macro:

@meta_macro(5)
println(@foo(3))
# 8

Okay, wasn't entirely sure that was going to work, but it appears to. 
However, if I try to move the exact same macro code into a module, it no 
longer works:

module meta_macro_mod

export @meta_macro, @foo

macro meta_macro(x)
  quote
macro foo(y)
  $x+y
end
  end
end

end

Even without trying to invoke `@foo`, when I execute `@meta_macro`, I get:

ERROR: syntax: invalid macro definition


It seems like how the macro gets evaluated changes when it's in the module. 
If I change it to a module to just doing an 'include', everything works 
again.


[julia-users] Re: macros generating macros in modules

2015-04-04 Thread Abe Schneider
The issue I'm dealing with is that I have a macro that I want to pass a 
list of functions that the macro can employ for parsing grammars. The macro 
itself exists already, and it currently has its own static list of 
functions. I'm trying to figure out a way to allow the user of the library 
to customize it.

For example:
@grammar foo begin
  start = list(integer, r, )
end

where `list` is a user supplied function. The issue that I keep running 
into is that there doesn't seem to be any easy way of just passing in a 
function to a macro. Turning an expression into a function is problematic, 
because `eval`s are: (a) only work in the modules namespace, and (b) are 
frowned on.

I've thought about manually looking up the symbol name in the various 
namespaces, but while I've found methods to list the functions, I haven't 
found a way to do the reverse.

Ideally, it would be nice to generate an expression with `call` that took a 
symbol and a namespace, that way no lookups would have to be done.

Having hit a dead end in this direction, it occurred to me that it might be 
possible to do something like this:
@set_parsers(list, etc)
@grammar foo begin
...
end


where '@set_parsers` would generate the `@grammar` macro with the static 
list it already has plus whatever else the user adds in.

Which works, except for the whole module issue.


Thanks,
A

On Saturday, April 4, 2015 at 12:41:27 PM UTC-4, Patrick O'Leary wrote:

 On Saturday, April 4, 2015 at 9:04:10 AM UTC-5, Abe Schneider wrote:

 I should start off, not entirely sure this is an okay thing to do with 
 Julia. Suppose I want to create a macro that generates another macro...


 I'm not sure whether this should work or not, but either way I'm not sure 
 how it's any more expressive than macros alone? Can you describe what it is 
 you want to do at a high level in a little more detail? There might be 
 another way. 



Re: [julia-users] Re: macros generating macros in modules

2015-04-04 Thread Abe Schneider
I don't understand how what I'm trying to do falls outside the domain of 
transforming code. My main goal is to take a user-defined grammar and 
create relevant code.

More to the point, I think the general ability to generate expressions 
based on functions/namespaces is also solidly in the domain of transforms. 
I can imagine plenty of use-cases for language-bindings, communication, etc.

Yes, there are many simple macros one can create, which are useful, but 
there exists many useful things one can do with macros that can get more 
complex.

A

On Saturday, April 4, 2015 at 10:11:25 PM UTC-4, Jameson wrote:

 I think the underlying issue may be that you are trying to have the macro 
 do too much, when you should instead be just doing source-code transforms 
 and preprocessing. One such example of a great use of a macro is simply:

 macro special_foo(syntax_tree)
 return quote
 special_foo( $(QuoteNode(syntax_tree) )
 end
 end


 On Sat, Apr 4, 2015 at 8:05 PM Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 The issue I'm dealing with is that I have a macro that I want to pass a 
 list of functions that the macro can employ for parsing grammars. The macro 
 itself exists already, and it currently has its own static list of 
 functions. I'm trying to figure out a way to allow the user of the library 
 to customize it.

 For example:
 @grammar foo begin
   start = list(integer, r, )
 end

 where `list` is a user supplied function. The issue that I keep running 
 into is that there doesn't seem to be any easy way of just passing in a 
 function to a macro. Turning an expression into a function is problematic, 
 because `eval`s are: (a) only work in the modules namespace, and (b) are 
 frowned on.

 I've thought about manually looking up the symbol name in the various 
 namespaces, but while I've found methods to list the functions, I haven't 
 found a way to do the reverse.

 Ideally, it would be nice to generate an expression with `call` that took 
 a symbol and a namespace, that way no lookups would have to be done.

 Having hit a dead end in this direction, it occurred to me that it might 
 be possible to do something like this:
 @set_parsers(list, etc)
 @grammar foo begin
 ...
 end


 where '@set_parsers` would generate the `@grammar` macro with the static 
 list it already has plus whatever else the user adds in.

 Which works, except for the whole module issue.


 Thanks,
 A


 On Saturday, April 4, 2015 at 12:41:27 PM UTC-4, Patrick O'Leary wrote:

 On Saturday, April 4, 2015 at 9:04:10 AM UTC-5, Abe Schneider wrote:

 I should start off, not entirely sure this is an okay thing to do with 
 Julia. Suppose I want to create a macro that generates another macro...


 I'm not sure whether this should work or not, but either way I'm not 
 sure how it's any more expressive than macros alone? Can you describe what 
 it is you want to do at a high level in a little more detail? There might 
 be another way. 



Re: [julia-users] Re: inserting an Expr into AST via macro

2015-03-24 Thread Abe Schneider
As a (hopeful) final note, I figured out the correct way to escape the 
expression:

  for rule in all_rules
if typeof(rule.action) != Function
  dot = Expr(:(.), rule, QuoteNode(:action))
  fn = Expr(:(-),
Expr(:tuple, :rule, :value, :first, :last, :children),
Expr(:block, rule.action))
  push!(code, Expr(:escape, Expr(:(=), dot, fn)))
end
  end


which seems to do the trick.

On Monday, March 23, 2015 at 8:00:23 AM UTC-4, Abe Schneider wrote:

 Okay, I think I almost have a solution. I now collect all the actions from 
 the rules with the function:

 function collect_rules(rule::Rule, lst::Array)
   push!(lst, rule)

   for child in get_children(rule)
 collect_rules(child, lst)
   end

   return lst
 end


 which is called from the loop:

 all_rules = Rule[]
 code = {}

 for definition in expr.args[2:2:end]
   name = string(definition.args[1])
   ref_by_name = Expr(:ref, :rules, name)

   rule = parseDefinition(name, definition.args[2], pdata)
   push!(code, :(rules[$name] = $rule))
   all_rules = collect_rules(rule, all_rules)
 end

 Finally, I add the transform to all the actions in the loop:

   for rule in all_rules
 if typeof(rule.action) != Function
   dot = Expr(:(.), rule, QuoteNode(:action))
   fn = Expr(:(-),
 Expr(:tuple, :rule, :value, :first, :last, :children),
 Expr(:block, rule.action))
   push!(code, Expr(:(=), dot, fn))
 end
   end


 Unfortunately, I'm still getting the namespace problem. I assume this is 
 because I'm not escaping properly in the macro. However, after playing 
 around with different variations, I can't figure out the proper place to 
 put the escape.

 Thanks for all the help!




 On Sunday, March 22, 2015 at 10:02:28 AM UTC-4, Jameson wrote:

 the trick with macros is that everything should be generating code, not 
 actually evaluating that code. think of it as a series of functions that do 
 a text transformation to a new structured document, not a [partial] 
 execution of that document. for example:

 function parseDefinition(name::String, expr::Expr, pdata::ParserData)
 #...
 elseif expr.head === :curly
   action_expr = expand_names(expr.args[2])
   rule_expr = parseDefinition(name, expr.args[1], action_expr, pdata)
 else
 #...
 return rule_expr
 end
 macro doAction(expr)
   return parseDefinition(..., expr, ...)
 end

 On Sun, Mar 22, 2015 at 8:15 AM Abe Schneider abe.schnei...@gmail.com 
 http://mailto:abe.schnei...@gmail.com wrote:

 I'm in the process of trying to figure out how to do something similar to 
 that, but it's unfortunately not easy. I was hoping that there might be a 
 method to insert an expression into the AST without an eval required, as it 
 would greatly simplify the code Jameson suggested using the `insert` macro, 
 which does as advertised, expect for the namespace issue.

 ​



Re: [julia-users] Re: inserting an Expr into AST via macro

2015-03-23 Thread Abe Schneider
Okay, I think I almost have a solution. I now collect all the actions from 
the rules with the function:

function collect_rules(rule::Rule, lst::Array)
  push!(lst, rule)

  for child in get_children(rule)
collect_rules(child, lst)
  end

  return lst
end


which is called from the loop:

all_rules = Rule[]
code = {}

for definition in expr.args[2:2:end]
  name = string(definition.args[1])
  ref_by_name = Expr(:ref, :rules, name)

  rule = parseDefinition(name, definition.args[2], pdata)
  push!(code, :(rules[$name] = $rule))
  all_rules = collect_rules(rule, all_rules)
end

Finally, I add the transform to all the actions in the loop:

  for rule in all_rules
if typeof(rule.action) != Function
  dot = Expr(:(.), rule, QuoteNode(:action))
  fn = Expr(:(-),
Expr(:tuple, :rule, :value, :first, :last, :children),
Expr(:block, rule.action))
  push!(code, Expr(:(=), dot, fn))
end
  end


Unfortunately, I'm still getting the namespace problem. I assume this is 
because I'm not escaping properly in the macro. However, after playing 
around with different variations, I can't figure out the proper place to 
put the escape.

Thanks for all the help!




On Sunday, March 22, 2015 at 10:02:28 AM UTC-4, Jameson wrote:

 the trick with macros is that everything should be generating code, not 
 actually evaluating that code. think of it as a series of functions that do 
 a text transformation to a new structured document, not a [partial] 
 execution of that document. for example:

 function parseDefinition(name::String, expr::Expr, pdata::ParserData)
 #...
 elseif expr.head === :curly
   action_expr = expand_names(expr.args[2])
   rule_expr = parseDefinition(name, expr.args[1], action_expr, pdata)
 else
 #...
 return rule_expr
 end
 macro doAction(expr)
   return parseDefinition(..., expr, ...)
 end

 On Sun, Mar 22, 2015 at 8:15 AM Abe Schneider abe.schnei...@gmail.com 
 http://mailto:abe.schnei...@gmail.com wrote:

 I'm in the process of trying to figure out how to do something similar to 
 that, but it's unfortunately not easy. I was hoping that there might be a 
 method to insert an expression into the AST without an eval required, as it 
 would greatly simplify the code Jameson suggested using the `insert` macro, 
 which does as advertised, expect for the namespace issue.

 ​



Re: [julia-users] Re: inserting an Expr into AST via macro

2015-03-23 Thread Abe Schneider
Sorry, I'm not being as precise I should with language, but I did mean 
'generate code to create a dictionary'. The macro exists already at the 
bottom of:

https://github.com/abeschneider/PEGParser.jl/blob/master/src/rules.jl

On Sunday, March 22, 2015 at 11:27:54 PM UTC-4, Jameson wrote:

 My macro’s primary role is to create a dictionary mapping symbols to Nodes. 
 Each Node has an associated action (passed in with the curly braces). The 
 actions themselves are Exprs, which need to be encapsulated as functions.

 that’s not something a macro can do (directly). and it's also why a macro 
 is different from a function.

 specifically, a function’s purpose is to change one object into another 
 thing. on the other hand, a macro is for transforming code into more code. 
 so the return value from the macro isn’t a new object, but the code that 
 describes how to to make that new object. so for the example above, rather 
 than directly assigning expr.args[2] into rule.action, you would return 
 the equivalent expression (quote; rule.action = $(expr.args[2]); end) 
 that do that operation at runtime

 On Sun, Mar 22, 2015 at 11:01 PM Abe Schneider abe.schnei...@gmail.com 
 http://mailto:abe.schnei...@gmail.com wrote:

 Sorry, when I said AST, I meant the code that gets executed. A macro, at 
 least the way I think about it, is inserting the resulting Expr into the 
 main AST.

 My macro's primary role is to create a dictionary mapping symbols to 
 `Node`s. Each Node has an associated action (passed in with the curly 
 braces). The actions themselves are `Expr`s, which need to be encapsulated 
 as functions.

 I was hoping initially that the `Expr` for the action could be converted 
 inline with the creation of the `Node`, as it would save the need of a lot 
 of book keeping. Thus, the: `rule.action = 
 insert_action_expr(expr.args[2])`.

 Another solution might to do two passes, where in the second pass the 
 rule's `Expr`s are converted. Unfortunately, that seems less elegant than 
 being able to convert an `Expr` to a function. 


 On Sunday, March 22, 2015 at 9:39:30 AM UTC-4, Toivo Henningsson wrote:

 Maybe there is a confusion of terms here? An Expr is the way to 
 represent an AST in Julia (some very simple ASTs are instead represented by 
 ints/floats/strings/symbols). So when you talk about inserting an Expr into 
 an AST it seems to me that all it means is to make an Expr where some 
 subtree is given by another Expr. 

 Macros are really only a way to save typing. Consider a few cases: what 
 is the input AST, and what is the output AST that you want to generate in 
 each case. From there, you should be able to figure out how to write the 
 code that does the transformation. 

 ​



Re: [julia-users] Re: inserting an Expr into AST via macro

2015-03-22 Thread Abe Schneider
I'm in the process of trying to figure out how to do something similar to 
that, but it's unfortunately not easy. I was hoping that there might be a 
method to insert an expression into the AST without an eval required, as it 
would greatly simplify the code Jameson suggested using the `insert` macro, 
which does as advertised, expect for the namespace issue.

On Sunday, March 22, 2015 at 2:15:17 AM UTC-4, Toivo Henningsson wrote:

 Do you really need to call eval from within a macro? That will indeed give 
 these kinds of troubles. Cannot you arrange for the macro to emit code that 
 sets the appropriate rule.action when run instead? Then you will be in the 
 invoker's context, and you can use esc. 



Re: [julia-users] Re: inserting an Expr into AST via macro

2015-03-22 Thread Abe Schneider
Sorry, when I said AST, I meant the code that gets executed. A macro, at 
least the way I think about it, is inserting the resulting Expr into the 
main AST.

My macro's primary role is to create a dictionary mapping symbols to 
`Node`s. Each Node has an associated action (passed in with the curly 
braces). The actions themselves are `Expr`s, which need to be encapsulated 
as functions.

I was hoping initially that the `Expr` for the action could be converted 
inline with the creation of the `Node`, as it would save the need of a lot 
of book keeping. Thus, the: `rule.action = 
insert_action_expr(expr.args[2])`.

Another solution might to do two passes, where in the second pass the 
rule's `Expr`s are converted. Unfortunately, that seems less elegant than 
being able to convert an `Expr` to a function. 


On Sunday, March 22, 2015 at 9:39:30 AM UTC-4, Toivo Henningsson wrote:

 Maybe there is a confusion of terms here? An Expr is the way to represent 
 an AST in Julia (some very simple ASTs are instead represented by 
 ints/floats/strings/symbols). So when you talk about inserting an Expr into 
 an AST it seems to me that all it means is to make an Expr where some 
 subtree is given by another Expr. 

 Macros are really only a way to save typing. Consider a few cases: what is 
 the input AST, and what is the output AST that you want to generate in each 
 case. From there, you should be able to figure out how to write the code 
 that does the transformation. 



Re: [julia-users] Re: inserting an Expr into AST via macro

2015-03-21 Thread Abe Schneider
Sadly it looks like this doesn't entirely solve the problem. The issue is 
that while it does indeed insert the function into the Expr tree, the 
namespace for the variables is for the module that the macro is defined in, 
and not the user's file (the standard issue with eval'ing).

For example, suppose I define a custom functions `foo` and `bar` in my file 
and define a rule like:

value = integer { foo(_1) } | float { bar(_1) }

the execution will fail since `foo` and `bar` are not defined.


On Thursday, March 19, 2015 at 9:59:19 AM UTC-4, Jameson wrote:

 yes and no. the definition of your insert_expr function below is:

 insert_expr(fn_expr) = @eval (rule, first, last, children) - $fn_expr

 so it’s not hard to define. but you could also just have 
 parse_action_definition return the necessary function in the first place.
 @eval is relatively expensive, since it will analyze the expression. this 
 is good, under the assumption that the resulting function will be reused 
 many times. but really bad if the user then tries to write a giant for loop 
 that repeated calls eval on the same thing. whereas wrapping the same 
 expression in an function, evaluating that once, then calling the function 
 repeatedly in the for loop lets the compiler optimize the loop much better. 
 eval is intentionally somewhat restricted in its abilities (such as not 
 being able to see local scope), specifically to make such abuses harder / 
 more obvious.

 On Thu, Mar 19, 2015 at 7:31 AM Abe Schneider abe.schnei...@gmail.com 
 http://mailto:abe.schnei...@gmail.com wrote: 

 Thank you Jameson, that makes a lot of sense. Generally I try to organize 
 my code to build up a single Expr, but sometimes it makes for less than 
 ideal code.

 Out of curiosity, would it make sense for Julia to have an 'insert' 
 function to convert Expr's to ASTs? This would help alleviate the need for 
 macros in certain cases as well 'eval'. For example, in my case, if I had:

 fn_expr = parse_action_definition(rule)  # fn(rule, first, last, children)
 rule.action = insert_expr(fn_expr)

 would cause `rule.action` be set to the actual function, rather than the 
 Expr. If you tried to use `eval`, not only is it frowned on, but it would 
 also fail because of it's global scope.

 While ultimately you can by, as you suggest, with building up the Exprs, I 
 think something like this would allow for easier to read/maintain code.



 On Thursday, March 19, 2015 at 12:43:29 AM UTC-4, Jameson wrote:

 writing a code snippet like

 val = :(parsefloat(3.1459))
 @test2(val)

 is perhaps a great way to confuse yourself, although it is a common 
 mistake.

 the problem is that it makes it seem like the two arguments execute in 
 sequence, whereas the macro expansion pass actually runs prior to the code 
 execution. it should, therefore, be viewed in complete isolation from the 
 runtime expressions. in pseudo-code, that might look something like:

 fullexpression = macroexpand(:(@test2(val)))
 ///
 val = :(parsefloat(3.1459))
 $fullexpression

 in summary, macros are functions whose arguments are syntax, not values. 
 when a macro is executed, val does not get passed as reference to a value 
 stored in a variable, it is the expression tree that describes that 
 variable. that is the fundamental distinction between a function and a 
 macro.

 but, it doesn't sound like you need a macro. macros that call other macros 
 can get really confusing really quickly. but a normal function will perhaps 
 do exactly what you wanted anyways? it's perfectly valid for you to write a 
 function that takes `val` in as an argument and returns some new expression 
 (which you can then combine with other expressions before returning the 
 whole thing from the main macro)


 On Wed, Mar 18, 2015 at 9:51 AM Abe Schneider abe.schnei...@gmail.com 
 http://mailto:abe.schnei...@gmail.com wrote:

 Unfortunately my solution only works if you pass in an expression 
 directly. If you try something like this:

 val = :(parsefloat(3.1459))
 @test2(val)

 It will fail, since `val` is a symbol. Any other ideas?


 The reason I'm trying to solve the problem in the first place is that I 
 have semantic actions attached to rules formed in a grammar. The actions 
 take the form of expression, which I want to wrap up in a function like:

 (rule,first, last,children) - $ex

 where `$ex` is my found expression. If I do this in my main macro, 
 everything work correctly. However, the logic gets more complicated, 
 because I want to allow semantic actions to be tied to any subrule, which 
 means it has to be handled in the definition parsing functions. That should 
 be fine, but I try to create a function that wraps my function, I get into 
 this issue. I can't just insert the expression into the AST like I did 
 before.in the main macro.


 On Wednesday, March 18, 2015 at 9:30:32 AM UTC-4, Abe Schneider wrote:

 After some thought, I realized that the easiest way to unquote is to reach 
 inside

Re: [julia-users] Re: inserting an Expr into AST via macro

2015-03-21 Thread Abe Schneider
I have, but it's not entirely clear to me how I would use it in this 
particular case. The code in question is being called from a function 
(which while ultimately is being called from a macro) doesn't directly 
return an expression in this case. Specifically, I have something that 
looks like:

insert_action_expr(fn_expr) = @eval (rule, value, first, last, children) - 
$fn_expr

function parseDefinition(name::String, expr::Expr, pdata::ParserData)
#...
elseif expr.head === :curly
  rule = parseDefinition(name, expr.args[1], pdata)
  action_expr = expand_names(expr.args[2])
  rule.action = insert_action_expr(action_expr)
else
#...
end

The issue is that `rule.action` eventually needs a function associated with 
it. The `insert_action_expr` takes the Expr that occurs in the braces and 
turns it into a function.

From my understanding, because this occurs within a function and it's not 
returning an Expr directly, `esc` isn't applicable.

On Saturday, March 21, 2015 at 11:02:28 AM UTC-4, Toivo Henningsson wrote:

 Have you read the macro hygiene section in the manual chapter about 
 metaprogramming? The esc function is what you want to be able to pass 
 through symbols to be evaluated in the invoker's name space.



Re: [julia-users] Re: inserting an Expr into AST via macro

2015-03-19 Thread Abe Schneider
Thank you Jameson, that makes a lot of sense. Generally I try to organize 
my code to build up a single Expr, but sometimes it makes for less than 
ideal code.

Out of curiosity, would it make sense for Julia to have an 'insert' 
function to convert Expr's to ASTs? This would help alleviate the need for 
macros in certain cases as well 'eval'. For example, in my case, if I had:

fn_expr = parse_action_definition(rule)  # fn(rule, first, last, children)
rule.action = insert_expr(fn_expr)

would cause `rule.action` be set to the actual function, rather than the 
Expr. If you tried to use `eval`, not only is it frowned on, but it would 
also fail because of it's global scope.

While ultimately you can by, as you suggest, with building up the Exprs, I 
think something like this would allow for easier to read/maintain code.


On Thursday, March 19, 2015 at 12:43:29 AM UTC-4, Jameson wrote:

 writing a code snippet like

 val = :(parsefloat(3.1459))
 @test2(val)

 is perhaps a great way to confuse yourself, although it is a common 
 mistake.

 the problem is that it makes it seem like the two arguments execute in 
 sequence, whereas the macro expansion pass actually runs prior to the code 
 execution. it should, therefore, be viewed in complete isolation from the 
 runtime expressions. in pseudo-code, that might look something like:

 fullexpression = macroexpand(:(@test2(val)))
 ///
 val = :(parsefloat(3.1459))
 $fullexpression

 in summary, macros are functions whose arguments are syntax, not values. 
 when a macro is executed, val does not get passed as reference to a value 
 stored in a variable, it is the expression tree that describes that 
 variable. that is the fundamental distinction between a function and a 
 macro.

 but, it doesn't sound like you need a macro. macros that call other macros 
 can get really confusing really quickly. but a normal function will perhaps 
 do exactly what you wanted anyways? it's perfectly valid for you to write a 
 function that takes `val` in as an argument and returns some new expression 
 (which you can then combine with other expressions before returning the 
 whole thing from the main macro)


 On Wed, Mar 18, 2015 at 9:51 AM Abe Schneider abe.schnei...@gmail.com 
 http://mailto:abe.schnei...@gmail.com wrote:

 Unfortunately my solution only works if you pass in an expression 
 directly. If you try something like this:

 val = :(parsefloat(3.1459))
 @test2(val)

 It will fail, since `val` is a symbol. Any other ideas?


 The reason I'm trying to solve the problem in the first place is that I 
 have semantic actions attached to rules formed in a grammar. The actions 
 take the form of expression, which I want to wrap up in a function like:

 (rule,first, last,children) - $ex

 where `$ex` is my found expression. If I do this in my main macro, 
 everything work correctly. However, the logic gets more complicated, 
 because I want to allow semantic actions to be tied to any subrule, which 
 means it has to be handled in the definition parsing functions. That should 
 be fine, but I try to create a function that wraps my function, I get into 
 this issue. I can't just insert the expression into the AST like I did 
 before.in the main macro.


 On Wednesday, March 18, 2015 at 9:30:32 AM UTC-4, Abe Schneider wrote:

 After some thought, I realized that the easiest way to unquote is to 
 reach inside the Expr and pull out what is needed. If I do a dump of `ex` I 
 get:

 Expr 
   head: Symbol quote
   args: Array(Any,(1,))
 1: Expr 
   head: Symbol call
   args: Array(Any,(2,))
 1: Symbol parsefloat
 2: ASCIIString 3.1459
   typ: Any


 So I can rewrite the macro as:

 macro test2(ex)
   ex.args[1]
 end

 which appears to work:

 @test2(:(parsefloat(3.1459)))

 # 3.1459





 On Wednesday, March 18, 2015 at 8:08:35 AM UTC-4, Abe Schneider wrote:

 If I do something simple like:

 macro test()
  :(parsefloat(3.1459))
 end

 @test() 

 # 3.1459

 everything works as expected. However, if I try this instead:

 macro test2(ex)
  ex
 end

 @test2(:(parsefloat(3.1459)))

 # :(parsefloat(3.1459))


 Not what I expected, but it makes sense what's happening:

 macroexpand(:(@test(:(parsefloat(3.1459)

 # :($(Expr(:copyast, :(:(parsefloat(3.1459))

 So, anything I pass to the macro is automatically quoted. Obviously if 
 I just do:

 @test2(parsefloat(3.1459))

 it will work. However, the use-case I'm trying to deal with is that I 
 have an Expr that I would like inserted into the AST. Besides being 
 frowned 
 on, I can't eval, due to not wanting things to be evaluated in global 
 space.

 Is there some way I can unquote the expression in the macro for test2?

 ​



Re: [julia-users] inserting an Expr into AST via macro

2015-03-18 Thread Abe Schneider
Thank you for the link. However, I am familiar with interpolation. What I 
don't understand is how you change `test2` in order to use it. Because 
there's no quote directly in that macro, Julia will complain about using 
'$' in a non-quoted expression.

On Wednesday, March 18, 2015 at 8:37:25 AM UTC-4, Isaiah wrote:

 See 
 http://docs.julialang.org/en/release-0.3/manual/metaprogramming/#interpolation
 On Mar 18, 2015 8:08 AM, Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 If I do something simple like:

 macro test()
  :(parsefloat(3.1459))
 end

 @test() 

 # 3.1459

 everything works as expected. However, if I try this instead:

 macro test2(ex)
  ex
 end

 @test2(:(parsefloat(3.1459)))

 # :(parsefloat(3.1459))


 Not what I expected, but it makes sense what's happening:

 macroexpand(:(@test(:(parsefloat(3.1459)

 # :($(Expr(:copyast, :(:(parsefloat(3.1459))

 So, anything I pass to the macro is automatically quoted. Obviously if I 
 just do:

 @test2(parsefloat(3.1459))

 it will work. However, the use-case I'm trying to deal with is that I 
 have an Expr that I would like inserted into the AST. Besides being frowned 
 on, I can't eval, due to not wanting things to be evaluated in global space.

 Is there some way I can unquote the expression in the macro for test2?



[julia-users] inserting an Expr into AST via macro

2015-03-18 Thread Abe Schneider
If I do something simple like:

macro test()
 :(parsefloat(3.1459))
end

@test() 

# 3.1459

everything works as expected. However, if I try this instead:

macro test2(ex)
 ex
end

@test2(:(parsefloat(3.1459)))

# :(parsefloat(3.1459))


Not what I expected, but it makes sense what's happening:

macroexpand(:(@test(:(parsefloat(3.1459)

# :($(Expr(:copyast, :(:(parsefloat(3.1459))

So, anything I pass to the macro is automatically quoted. Obviously if I 
just do:

@test2(parsefloat(3.1459))

it will work. However, the use-case I'm trying to deal with is that I have 
an Expr that I would like inserted into the AST. Besides being frowned on, 
I can't eval, due to not wanting things to be evaluated in global space.

Is there some way I can unquote the expression in the macro for test2?


[julia-users] Re: inserting an Expr into AST via macro

2015-03-18 Thread Abe Schneider
After some thought, I realized that the easiest way to unquote is to reach 
inside the Expr and pull out what is needed. If I do a dump of `ex` I get:

Expr 
  head: Symbol quote
  args: Array(Any,(1,))
1: Expr 
  head: Symbol call
  args: Array(Any,(2,))
1: Symbol parsefloat
2: ASCIIString 3.1459
  typ: Any


So I can rewrite the macro as:

macro test2(ex)
  ex.args[1]
end

which appears to work:

@test2(:(parsefloat(3.1459)))

# 3.1459





On Wednesday, March 18, 2015 at 8:08:35 AM UTC-4, Abe Schneider wrote:

 If I do something simple like:

 macro test()
  :(parsefloat(3.1459))
 end

 @test() 

 # 3.1459

 everything works as expected. However, if I try this instead:

 macro test2(ex)
  ex
 end

 @test2(:(parsefloat(3.1459)))

 # :(parsefloat(3.1459))


 Not what I expected, but it makes sense what's happening:

 macroexpand(:(@test(:(parsefloat(3.1459)

 # :($(Expr(:copyast, :(:(parsefloat(3.1459))

 So, anything I pass to the macro is automatically quoted. Obviously if I 
 just do:

 @test2(parsefloat(3.1459))

 it will work. However, the use-case I'm trying to deal with is that I have 
 an Expr that I would like inserted into the AST. Besides being frowned on, 
 I can't eval, due to not wanting things to be evaluated in global space.

 Is there some way I can unquote the expression in the macro for test2?



[julia-users] Re: inserting an Expr into AST via macro

2015-03-18 Thread Abe Schneider
Unfortunately my solution only works if you pass in an expression directly. 
If you try something like this:

val = :(parsefloat(3.1459))
@test2(val)

It will fail, since `val` is a symbol. Any other ideas?


The reason I'm trying to solve the problem in the first place is that I 
have semantic actions attached to rules formed in a grammar. The actions 
take the form of expression, which I want to wrap up in a function like:

(rule,first, last,children) - $ex

where `$ex` is my found expression. If I do this in my main macro, 
everything work correctly. However, the logic gets more complicated, 
because I want to allow semantic actions to be tied to any subrule, which 
means it has to be handled in the definition parsing functions. That should 
be fine, but I try to create a function that wraps my function, I get into 
this issue. I can't just insert the expression into the AST like I did 
before.in the main macro.


On Wednesday, March 18, 2015 at 9:30:32 AM UTC-4, Abe Schneider wrote:

 After some thought, I realized that the easiest way to unquote is to reach 
 inside the Expr and pull out what is needed. If I do a dump of `ex` I get:

 Expr 
   head: Symbol quote
   args: Array(Any,(1,))
 1: Expr 
   head: Symbol call
   args: Array(Any,(2,))
 1: Symbol parsefloat
 2: ASCIIString 3.1459
   typ: Any


 So I can rewrite the macro as:

 macro test2(ex)
   ex.args[1]
 end

 which appears to work:

 @test2(:(parsefloat(3.1459)))

 # 3.1459





 On Wednesday, March 18, 2015 at 8:08:35 AM UTC-4, Abe Schneider wrote:

 If I do something simple like:

 macro test()
  :(parsefloat(3.1459))
 end

 @test() 

 # 3.1459

 everything works as expected. However, if I try this instead:

 macro test2(ex)
  ex
 end

 @test2(:(parsefloat(3.1459)))

 # :(parsefloat(3.1459))


 Not what I expected, but it makes sense what's happening:

 macroexpand(:(@test(:(parsefloat(3.1459)

 # :($(Expr(:copyast, :(:(parsefloat(3.1459))

 So, anything I pass to the macro is automatically quoted. Obviously if I 
 just do:

 @test2(parsefloat(3.1459))

 it will work. However, the use-case I'm trying to deal with is that I 
 have an Expr that I would like inserted into the AST. Besides being frowned 
 on, I can't eval, due to not wanting things to be evaluated in global space.

 Is there some way I can unquote the expression in the macro for test2?



Re: [julia-users] creation of parametric variables in a macro

2015-03-07 Thread Abe Schneider
Awesome, thanks for the suggestions. I ended up independently implementing 
your second solution, which I think is the more elegant way to do it. But 
it's good to know about the first approach as well.

For anyone who is interested, here's the code I ended up with:

# general case, just return value
expand_names(value) = value

# if it's a symbol, check that it matches, and if so, convert it
function expand_names(sym::Symbol)
  m = match(r_(\d+), string(sym))
  if m !== nothing
return :(children[parseint($(m.captures[1]))])
  end
  return sym
end

# if it's an expression, recursively go through tree and
# transform all symbols that match '_i'
function expand_names(expr::Expr)
  new_args = [expand_names(arg) for arg in expr.args]
  return Expr(expr.head, new_args...)
end


Then, you can can run expand_names on any expression/symbol passed via the 
braces.


On Friday, March 6, 2015 at 10:58:43 PM UTC-5, Jameson wrote:

 oh, that’s reasonably easy then:

 macro testfn(expr)
 children = esc(:children)
 syms = [:($(symbol(string(_, i))) = $children[$i]) for i = 1:10]
 return Expr(:let, Expr(:block, esc(expr)), :(children=children), syms..)
 end

 which will expand to:

 let children=children, _1 = children[1], _2 = children[2], ...
$expr
 end

 (I added the first children=children line, so that the user could 
 theoretically assign to a variable named children, without leaking it to 
 the enclosing environment. it's not strictly necessary).

 -

 alternatively, you could recurse through their expr code and replace all 
 variables of the form `_(\d+)` with :(children[\1])

 -


 On Fri, Mar 6, 2015 at 9:30 PM Abe Schneider abe.schnei...@gmail.com 
 http://mailto:abe.schnei...@gmail.com wrote:

 Hmmm, good to know. Thank you.

  The rationale for doing so is to provide a shortcut for the elements of 
 a variable `children`. Specifically, for a grammar, I might have a rule 
 like:

 ```
 @grammar foo begin
number = r[0-9]+ { parseint(children[1]) }
 end
 ```

 What I would like to have instead, to make it more succint is:

 ```
 @grammar foo begin
number = r[0-9]+ { parseint(_1) }
 end
 ```

 Originally, just to get things working, I used an `eval`, which while 
 worked, also made the assignment global, which was less than ideal.


 I'd be curious if anyone has a suggestion on other methods to accomplish 
 this, or if this is outside the scope of what's possible to do with Julia.



 On Friday, March 6, 2015 at 5:10:07 PM UTC-5, Jameson wrote:

 you can't do what you are proposing, by design. a macro cannot do 
 anything that you cannot express directly, it simply allows you to express 
 it more succinctly by templating the redundant parts.

 if you want a set or numbered list, use a set or number list. 
 variables are bad at that sort of task. whereas an Array is very good at it.

 On Fri, Mar 6, 2015 at 8:05 AM Abe Schneider abe.sc...@gmail.com 
 wrote:

 I'm trying to create a set of variables (_1, _2, ...) from items within 
 a list in a macro. I have a (much) condensed version of the code:

 macro testfn()
 quote
 i = 1
 value = [1, 2, 3]
 $(Expr(:(=), Expr(:symbol, Expr(:string, _, :i)), :value))
 println(_1)
 end
 end


 which gives me:

 ERROR: syntax: invalid assignment location


 Any ideas on what might be wrong or the proper way to do this? I would 
 like to keep this in the quotes, as in the actual version there's a lot 
 more code surrounding the assignment.

 I can get things to work with an eval, but I rather avoid the eval, and 
 it appears to create a non-local variable.


 Thanks!

  ​



Re: [julia-users] creation of parametric variables in a macro

2015-03-06 Thread Abe Schneider
Hmmm, good to know. Thank you.

 The rationale for doing so is to provide a shortcut for the elements of a 
variable `children`. Specifically, for a grammar, I might have a rule like:

```
@grammar foo begin
   number = r[0-9]+ { parseint(children[1]) }
end
```

What I would like to have instead, to make it more succint is:

```
@grammar foo begin
   number = r[0-9]+ { parseint(_1) }
end
```

Originally, just to get things working, I used an `eval`, which while 
worked, also made the assignment global, which was less than ideal.


I'd be curious if anyone has a suggestion on other methods to accomplish 
this, or if this is outside the scope of what's possible to do with Julia.


On Friday, March 6, 2015 at 5:10:07 PM UTC-5, Jameson wrote:

 you can't do what you are proposing, by design. a macro cannot do anything 
 that you cannot express directly, it simply allows you to express it more 
 succinctly by templating the redundant parts.

 if you want a set or numbered list, use a set or number list. 
 variables are bad at that sort of task. whereas an Array is very good at it.

 On Fri, Mar 6, 2015 at 8:05 AM Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 I'm trying to create a set of variables (_1, _2, ...) from items within a 
 list in a macro. I have a (much) condensed version of the code:

 macro testfn()
 quote
 i = 1
 value = [1, 2, 3]
 $(Expr(:(=), Expr(:symbol, Expr(:string, _, :i)), :value))
 println(_1)
 end
 end


 which gives me:

 ERROR: syntax: invalid assignment location


 Any ideas on what might be wrong or the proper way to do this? I would 
 like to keep this in the quotes, as in the actual version there's a lot 
 more code surrounding the assignment.

 I can get things to work with an eval, but I rather avoid the eval, and 
 it appears to create a non-local variable.


 Thanks!



[julia-users] creation of parametric variables in a macro

2015-03-06 Thread Abe Schneider
I'm trying to create a set of variables (_1, _2, ...) from items within a 
list in a macro. I have a (much) condensed version of the code:

macro testfn()
quote
i = 1
value = [1, 2, 3]
$(Expr(:(=), Expr(:symbol, Expr(:string, _, :i)), :value))
println(_1)
end
end


which gives me:

ERROR: syntax: invalid assignment location


Any ideas on what might be wrong or the proper way to do this? I would like 
to keep this in the quotes, as in the actual version there's a lot more 
code surrounding the assignment.

I can get things to work with an eval, but I rather avoid the eval, and it 
appears to create a non-local variable.


Thanks!


[julia-users] assignment operator

2014-10-18 Thread Abe Schneider
I was recently thinking about the nature of `=` of not being an operator. 
The reason given is that it sets the binding of the variable, rather than 
the value. It seems like it would be nice to have an operator that dealt 
with values rather than bindings. The reason being: (a) if it's an operator 
you can overload its behavior, which when dealing with values could be very 
useful, and (b) it provides a more natural syntax than `copy`.

While I don't have strong feels about any particular syntax, I could 
imagine something like:
x := y # copied
x = y  # bound

function :=(var, value)
#...
end

One side benefit of doing is this it can help solve other issues. For 
example, you could make a `ref` class for cases where you want to pass a 
variable bound to a scalar to be altered within a function:
type ref{T}
  var::T
end

function :={T}(var::ref{T}, value::T)
  ref.var := value
end



[julia-users] Abstract types with fields

2014-09-06 Thread Abe Schneider
Don't worry, I'm not re-opening the currently debated issue . It occurred 
to me a while ago that it should be possible to support this feature 
without any changes to the language itself. 

Instead I've created the macros `@_abstract`, `@_type`, and `@_immutable`. 
The idea is that `@_abstract` does two things:

   1. It adds the fields to a global registry and creates an abstract class 
   with the given name
   2. When a @_type or @_immutable is created, it copies the fields from 
   the abstract registry and adds its own


The current working code can be found at: 
https://github.com/abeschneider/AbstractFields.jl

A quick example:

@_abstract Point begin
  x::Float64
  y::Float64
end

@_type 3DPoint Point begin
  z::Float64
end

# create a 3DPoint (abstract's values get filled first)
point = 3DPoint(1.0, 1.0, 1.0)


One of the main advantages of using these macros is that you know if you 
have a function that takes a `Point`, it will have `x` and `y` defined. As 
has been pointed out, this isn't strictly necessary, as you could provide 
an interface with `getx`, `gety`, `setx`, `sety` for each subclass of 
`Point`. However, this can result in a lot of extra boilerplate code.


Anyways, I'm not sure if this is useful/interesting to anyone else, but 
it's something I've wanted for my own code.


[julia-users] Re: Function with state calling stateless version, or the other way around?

2014-08-25 Thread Abe Schneider
You can think of a Task like a function that maintains state automatically. 
However, instead of using returning values with 'return x', you use 
'produce(x)' instead.

This will cause execution of the Task to pause until it is called again. Tasks 
are called with the 'consume' function, which will in turn return the value 
given by the 'produce'.

The official Julia documentation gives code examples of how to create and use 
tasks. In the case of the documentation, a task is returned from within a 
function. The variables defined in the function get bound to the Task returned, 
which in turn are modified between each call to consume. Julia allows you to 
also use Tasks as iterators.

You can get similar behavior with returning a function from a function. The 
inner function will be bound to the outer function's variables and can modify 
them. If the variables are scalars, they will be copied, if they are complex 
types a reference is created.


[julia-users] Function with state calling stateless version, or the other way around?

2014-08-23 Thread Abe Schneider
It may be worth having both around. If you wrap the stateless versions with 
something that keeps state, users get the choice of which one to use.

For example, you could use Tasks to create generators that produce the next 
value. The Task will keep the state for you, which allows you to keep your DSP 
code simple and stateless.


[julia-users] Grammatical Evolution

2014-08-15 Thread Abe Schneider
For anyone who is interested, I've been working on a Grammatical Evolution 
(GE) [Conor Ryan, JJ Collins and Michael O'Neill, 1998] 
http://en.wikipedia.org/wiki/Grammatical_evolution#cite_note-1 library:

https://github.com/abeschneider/GrammaticalEvolution

It is not quite ready to reach version 0.0.0, though it does have decent 
test coverage. Included is an example to optimize a mathematical expression 
to match some arbitrary ground truth.

For those who are not familiar with (GE), it is an Evolutionary Technique 
that is similar to Genetic Programming (GP). However, unlike GP, it doesn't 
suffer the same problems with fixing damaged trees. Instead, it uses a 
grammar that is combined with a genome of integers. The genome is used to 
select which branch to follow for or-rules.

Julia is a really nice language to implement GE due to its ability to 
inject new code into the current program (thus no need for an auxiliary 
grammar or parsing of strings) as well as macros that allow a grammar to be 
easily defined. Add to that the ability to easily distribute code that can 
be compiled in a JIT manner means it's possible to get very good speeds 
with the library (note: currently no benchmarking has been done and I still 
haven't written the code to distribute the workload).
 


[julia-users] Re: Equivalent of c++ functor objects, std::bind, and lambdas

2014-08-15 Thread Abe Schneider
Here's a quick test:

function make_counter(x)
  return (delta) - begin
x += delta
x
  end
end

c0 = make_counter(0)
c1 = make_counter(0)

c0(1) # 1
c1(1) # 1
c0(1) # 2
c1(1) # 2

So it looks like they don't share the bound 'x' variable.


On Friday, August 15, 2014 11:50:03 AM UTC-4, Noah Brenowitz wrote:

 suppose I have a function with prototype  f(x, y, z). How can bind one 
 of the arguments to a new function argument by copying vs reference? In 
 c++11 I could do 

 z = ... ;
 auto newfun = [=](x,y) { f(x,y, z)}; 

 if I wanted newfun to have its own copy of z. Then I could make some 
 changes to original object z without affecting the evaluation of newfun. An 
 alternative way to do this would be using a Functor class or std::bind. 
 Is it possible to replicate this behavior in julia? 



Re: [julia-users] Using a callback from a macro

2014-08-09 Thread Abe Schneider
I still haven't been able to get the code to work with using quotes. 
However, with some experimentation I was able to write things out directly 
with Exprs. A condensed version of the code is:

macro grammar(grammar_name::Symbol, ex::Expr)
  code = {}
  push!(code, :(rules = Dict()))

  for definition in ex.args[2:2:end]
name = Expr(:call, :string, Expr(:quote, definition.args[1]))
ex = Expr(:quote, definition.args[2])
action = Expr(:escape, definition.args[1].args[2])
  
# rules[name] = parseDefinition(name, ex, nothing)
push!(code, Expr(:(=), Expr(:ref, :rules, name), 
Expr(:call, :parseDefinition, name, ex, action)))
  end

  # grammar_name = Grammar(rules)
  push!(code, :($(esc(grammar_name)) = Grammar(rules)))
  return Expr(:block, code...)
end

The tricky part being the definition of `action`. It can't be evaluated in 
the macro itself, as it would be in the wrong namespace, and thus had to be 
escaped. In a separate thread Tim Holy provided a method to get the 
expression passed to the `parseDefinition` method, but I couldn't get it to 
work with everything else.

I actually think keeping everything as `Expr`s is easier to understand, 
though I'm still curious how to properly express this in quote form.


On Thursday, August 7, 2014 1:51:30 PM UTC-4, Jameson wrote:

 A function which has access to the namespace in which it was defined is 
 also known in Julia as a closure, or simply function. All functions are 
 first-class objects, which don't need eval or macros. Eval and macros are 
 really bad at pretending to be functions. 

 Without a bit more example code, it is hard to understand what problem you 
 are trying to solve. Macros are for reducing typing (syntax transforms), 
 not magic (altering the environment), which is why they generally don't 
 have access to the environment. 

 On Friday, August 1, 2014, Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 I tried a second approach where instead of keeping a function around I 
 keep just the symbol. I have a `transform` function that applies the 
 function to the resulting values. However, this only moves the problem to a 
 new place. In my `transform` method I have:

 eval(Expr(:call, action, values))


 where `action` is the symbol that I am now carrying around. The `eval` 
 still works in the module's namespace, so I get the same error.

 If Julia had a way to access the namespace from the calling function, 
 this could be made to work. Or for that matter, if I could get the calling 
 namespace from the macro, I could then just get the macro that way.

 I'm guessing Julia doesn't currently have this functionality, but would 
 it be something possible to add?

 On Friday, August 1, 2014 12:22:46 PM UTC-4, Abe Schneider wrote:

 I think the problem is that I'm not accessing it directly through the 
 macro parameters. The call:

 @grammar foo begin ... end

 passes just the single expression block to `foo`. Thus, I'm getting the 
 function from the resulting Expr tree. Even if I quote it, it still ends up 
 as an expression that contains a symbol that must be evaluated (unless I'm 
 missing something...)


 On Friday, August 1, 2014 11:42:52 AM UTC-4, Simon Kornblith wrote:

 That looks like the output of :(esc(fn)), but you don't want to quote 
 that, you want to evaluate it when generating the code, i.e. use 
 $(esc(fn)) wherever you were previously using $fn

 On Friday, August 1, 2014 11:38:44 AM UTC-4, Abe Schneider wrote:

 That's correct, I'm generating code that keeps a pointer to that 
 function to call later on.

 If I do that, I have the type `esc(fn)` in the macro (this is what I 
 get when printing it out), and taking a dump of that argument gives:

 Expr 
   head: Symbol call
   args: Array(Any,(2,))
 1: Symbol esc
 2: Symbol fn
   typ: Any


 Does that mean instead of carrying around a function I will need to 
 carry around the Expr?

 Thanks!

 On Friday, August 1, 2014 11:17:50 AM UTC-4, Simon Kornblith wrote:

 Assuming you're generating code that calls fn, as opposed to trying 
 to call it when generating code in the macro (usually a bad idea), you 
 should use esc(fn) in place of fn

 On Friday, August 1, 2014 10:50:15 AM UTC-4, Abe Schneider wrote:

 I've come across a problem where I have macro to define  a grammar 
 (similar to how PEGParser currently works):

 @grammar foo begin
   rule[fn] = some + (rule | test)
 end

 where the `[fn]` next to the rule defines a function to call on the 
 results (in this case it's an expansion). The issue is that parsing the 
 Expr tree, `fn` is given as a Symbol (which makes sense).

 However, if I try to turn `fn` into a function I run into the 
 namespace issue I've had previously. If `fn` is defined in my module, 
 it 
 works without problem. If it's defined in the code that imports the 
 module, 
 it will not work because that function doesn't exist in the namespace 
 of 
 the module.

 I'm guessing there isn't an easy

[julia-users] Passing an expression from a macro to a function

2014-08-03 Thread Abe Schneider
I found one previous conversation related to this, but unfortunately the 
answer didn't work for me. Hopefully I'm not asking an obvious question.

Suppose I have some macro:
macro mytest(fn::Symbol, ex::Expr)
  quote
$(esc(fn))($ex)
  end
end

and I have some function that takes in the expression to operate on it:
myfun(ex::Expr) = ...

the problem (which may be obvious) is that `$ex` gets evaluated with the 
macro, and I won't pass an `Expr` to `myfun`. A quick demonstration:

foo(x, y) = x+y
println(expandmacro(:(@mytest foo 1+2)))

gives:
begin  # .../mtestmod.jl, line 38:
foo(mtestmod.+(1,2))
end

What I can't figure out is how to keep `ex` an expression that is passed to 
foo (at least without writing out Expr by hand). I've tried many 
combinations of syntax to try to preserve the Expr-ness of `ex`.

Thanks!


Re: [julia-users] Passing an expression from a macro to a function

2014-08-03 Thread Abe Schneider
Awesome, that works. Thank you!

Is there some master list of these macro-tricks? An IPython-type worksheet 
might serve as a nice look-up table for how to get things done with macros.

On Sunday, August 3, 2014 3:04:53 PM UTC-4, Tim Holy wrote:

 It's not obvious. Try this: 

 macro mytest(fn::Symbol, ex::Expr) 
  qex = Expr(:quote, ex)  # here's the magic incantation 
  quote 
$(esc(fn))($qex) 
  end 
 end 

 Works for symbols that you want to keep as symbols, too. 

 But your `foo` method is not defined for an expression, so your test case 
 will 
 throw an error. 

 --Tim 

 On Sunday, August 03, 2014 11:46:43 AM Abe Schneider wrote: 
  I found one previous conversation related to this, but unfortunately the 
  answer didn't work for me. Hopefully I'm not asking an obvious question. 
  
  Suppose I have some macro: 
  macro mytest(fn::Symbol, ex::Expr) 
quote 
  $(esc(fn))($ex) 
end 
  end 
  
  and I have some function that takes in the expression to operate on it: 
  myfun(ex::Expr) = ... 
  
  the problem (which may be obvious) is that `$ex` gets evaluated with the 
  macro, and I won't pass an `Expr` to `myfun`. A quick demonstration: 
  
  foo(x, y) = x+y 
  println(expandmacro(:(@mytest foo 1+2))) 
  
  gives: 
  begin  # .../mtestmod.jl, line 38: 
  foo(mtestmod.+(1,2)) 
  end 
  
  What I can't figure out is how to keep `ex` an expression that is passed 
 to 
  foo (at least without writing out Expr by hand). I've tried many 
  combinations of syntax to try to preserve the Expr-ness of `ex`. 
  
  Thanks! 



[julia-users] Using a callback from a macro

2014-08-01 Thread Abe Schneider
I've come across a problem where I have macro to define  a grammar (similar 
to how PEGParser currently works):

@grammar foo begin
  rule[fn] = some + (rule | test)
end

where the `[fn]` next to the rule defines a function to call on the results 
(in this case it's an expansion). The issue is that parsing the Expr tree, 
`fn` is given as a Symbol (which makes sense).

However, if I try to turn `fn` into a function I run into the namespace 
issue I've had previously. If `fn` is defined in my module, it works 
without problem. If it's defined in the code that imports the module, it 
will not work because that function doesn't exist in the namespace of the 
module.

I'm guessing there isn't an easy solution to fix this problem, but I 
thought I'd check to see if someone had an idea.

Thanks!



[julia-users] Re: Using a callback from a macro

2014-08-01 Thread Abe Schneider
I think the problem is that I'm not accessing it directly through the macro 
parameters. The call:

@grammar foo begin ... end

passes just the single expression block to `foo`. Thus, I'm getting the 
function from the resulting Expr tree. Even if I quote it, it still ends up 
as an expression that contains a symbol that must be evaluated (unless I'm 
missing something...)


On Friday, August 1, 2014 11:42:52 AM UTC-4, Simon Kornblith wrote:

 That looks like the output of :(esc(fn)), but you don't want to quote 
 that, you want to evaluate it when generating the code, i.e. use 
 $(esc(fn)) wherever you were previously using $fn

 On Friday, August 1, 2014 11:38:44 AM UTC-4, Abe Schneider wrote:

 That's correct, I'm generating code that keeps a pointer to that function 
 to call later on.

 If I do that, I have the type `esc(fn)` in the macro (this is what I get 
 when printing it out), and taking a dump of that argument gives:

 Expr 
   head: Symbol call
   args: Array(Any,(2,))
 1: Symbol esc
 2: Symbol fn
   typ: Any


 Does that mean instead of carrying around a function I will need to carry 
 around the Expr?

 Thanks!

 On Friday, August 1, 2014 11:17:50 AM UTC-4, Simon Kornblith wrote:

 Assuming you're generating code that calls fn, as opposed to trying to 
 call it when generating code in the macro (usually a bad idea), you should 
 use esc(fn) in place of fn

 On Friday, August 1, 2014 10:50:15 AM UTC-4, Abe Schneider wrote:

 I've come across a problem where I have macro to define  a grammar 
 (similar to how PEGParser currently works):

 @grammar foo begin
   rule[fn] = some + (rule | test)
 end

 where the `[fn]` next to the rule defines a function to call on the 
 results (in this case it's an expansion). The issue is that parsing the 
 Expr tree, `fn` is given as a Symbol (which makes sense).

 However, if I try to turn `fn` into a function I run into the namespace 
 issue I've had previously. If `fn` is defined in my module, it works 
 without problem. If it's defined in the code that imports the module, it 
 will not work because that function doesn't exist in the namespace of the 
 module.

 I'm guessing there isn't an easy solution to fix this problem, but I 
 thought I'd check to see if someone had an idea.

 Thanks!



[julia-users] Re: Using a callback from a macro

2014-08-01 Thread Abe Schneider
I tried a second approach where instead of keeping a function around I keep 
just the symbol. I have a `transform` function that applies the function to 
the resulting values. However, this only moves the problem to a new place. 
In my `transform` method I have:

eval(Expr(:call, action, values))


where `action` is the symbol that I am now carrying around. The `eval` 
still works in the module's namespace, so I get the same error.

If Julia had a way to access the namespace from the calling function, this 
could be made to work. Or for that matter, if I could get the calling 
namespace from the macro, I could then just get the macro that way.

I'm guessing Julia doesn't currently have this functionality, but would it 
be something possible to add?

On Friday, August 1, 2014 12:22:46 PM UTC-4, Abe Schneider wrote:

 I think the problem is that I'm not accessing it directly through the 
 macro parameters. The call:

 @grammar foo begin ... end

 passes just the single expression block to `foo`. Thus, I'm getting the 
 function from the resulting Expr tree. Even if I quote it, it still ends up 
 as an expression that contains a symbol that must be evaluated (unless I'm 
 missing something...)


 On Friday, August 1, 2014 11:42:52 AM UTC-4, Simon Kornblith wrote:

 That looks like the output of :(esc(fn)), but you don't want to quote 
 that, you want to evaluate it when generating the code, i.e. use 
 $(esc(fn)) wherever you were previously using $fn

 On Friday, August 1, 2014 11:38:44 AM UTC-4, Abe Schneider wrote:

 That's correct, I'm generating code that keeps a pointer to that 
 function to call later on.

 If I do that, I have the type `esc(fn)` in the macro (this is what I get 
 when printing it out), and taking a dump of that argument gives:

 Expr 
   head: Symbol call
   args: Array(Any,(2,))
 1: Symbol esc
 2: Symbol fn
   typ: Any


 Does that mean instead of carrying around a function I will need to 
 carry around the Expr?

 Thanks!

 On Friday, August 1, 2014 11:17:50 AM UTC-4, Simon Kornblith wrote:

 Assuming you're generating code that calls fn, as opposed to trying to 
 call it when generating code in the macro (usually a bad idea), you should 
 use esc(fn) in place of fn

 On Friday, August 1, 2014 10:50:15 AM UTC-4, Abe Schneider wrote:

 I've come across a problem where I have macro to define  a grammar 
 (similar to how PEGParser currently works):

 @grammar foo begin
   rule[fn] = some + (rule | test)
 end

 where the `[fn]` next to the rule defines a function to call on the 
 results (in this case it's an expansion). The issue is that parsing the 
 Expr tree, `fn` is given as a Symbol (which makes sense).

 However, if I try to turn `fn` into a function I run into the 
 namespace issue I've had previously. If `fn` is defined in my module, it 
 works without problem. If it's defined in the code that imports the 
 module, 
 it will not work because that function doesn't exist in the namespace of 
 the module.

 I'm guessing there isn't an easy solution to fix this problem, but I 
 thought I'd check to see if someone had an idea.

 Thanks!



[julia-users] overloading an abstract interface

2014-07-26 Thread Abe Schneider
I have a pattern that has come up multiple times where in a module I might 
have some function `foo` which will call some other function `bar` on a 
given type. The exact function `bar` isn't defined yet because it is 
defined by the user-type. The problem I run into is that if `bar` is 
defined outside of the module, `foo` won't see it.

Here is a simple example:
module testmod

export foo, Baz

abstract Baz

bar(x::Baz) = nothing

function foo(x::Baz)
return bar(x)
end

end

with the user-defined code:
using testmod

type ConcreteBaz : Baz
  value::Int64
end

function bar(baz::ConcreteBaz)
return baz.value
end

baz = ConcreteBaz(42)
println(result = $(foo(baz)))

The output is `result = nothing`, and thus the wrong function is called. If 
I move all of the code to the same file it works.

My question is: is this expected behavior? If so, what's the proper way of 
creating an interface for an abstract type which can later be overridden in 
a user file?


[julia-users] Re: overloading an abstract interface

2014-07-26 Thread Abe Schneider
Thank you. If I do:

function testmodule.bar(baz::ConcreteBaz)
  return baz.value
end

it works. I'm guessing this means that Julia won't look outside of the 
namespace for a function.

It hadn't occurred to me that writing:

function module.fn()
  # ...
end

would work.


On Saturday, July 26, 2014 6:23:16 PM UTC-4, Ivar Nesje wrote:

 Yes, this is expected behavior.

 You will have to define testmodule.baz() to not create a new function, but 
 extend the existing function with a new method. 



[julia-users] A julia version of diy-lisp (python project)

2014-07-20 Thread Abe Schneider
If you're interested, PEGParser includes a lisp grammar in the examples 
section. The transform converts to Julia expressions, but that can easily be 
changed.


[julia-users] Sorting behavior

2014-07-20 Thread Abe Schneider
It wasn't obvious to me initially why `sort` wasn't working for me (strings 
and composite types). On further investigation it looks like that it only 
works for single-dimension arrays -- which makes sense. However, if I type:

lst = [a b c]
sort(lst)

I get an error. The answer is that it's of type `Array{ASCIIString, 2}`, 
whereas `sort` wants the type to be `Array{ASCIIString, 1}`. The correct 
solution is to write this instead:

lst = [a, b, c]
sort(lst)

The problem seems to derive from two design decisions:

   1. It is not obvious to someone new to Julia why one form gives a two 
   dimensional array whereas the other gives a one dimensional array.
   2. `sort` doesn't try to determine if the array passed is actually jeust 
   one dimensional.

I'm not sure there is a simple solution. I assume there's a good reason for 
(1) and (2) involves some overhead which might be undesirable.


Re: [julia-users] PEG Parser

2014-07-13 Thread Abe Schneider
I agree, I think PEG grammars are likely not well-suited to parsing large 
amounts of data (especially where a hand-crafted parser can be created). 
That said, I am curious as to why the speed difference exists. In the case 
of CSV, I think the packrat caching mechanism probably doesn't help, but 
disabling that is still slow.

The next logical point of slowness is the number of function-calls 
required. I know that the multi-dispatch has some added penalty over 
single-dispatch, but I'm not sure by how much. It's possible that I could 
rewrite some of the CSV grammar to make less calls by either rewriting some 
of the rules or by using more regular expressions.

Finally, the last likely place for the slow-down is the fact that PEGParser 
has to create the AST as it goes along. This is a huge overhead that the 
DataFrames CSV parser does not need to do since it's a single-purpose 
parser.

I'm going to continue work on the Dot parser as I think it's probably more 
useful (and more difficult to write by hand).

Also, I've created a pull request to add PEGParser to the official package 
list. If it's something that interests other people, it would be great to 
have other people involved.

On Sunday, July 6, 2014 9:08:40 PM UTC-4, John Myles White wrote:ly,, 

 Thanks for looking into this, Abe. That’s too bad that the CSV parser is 
 much slower than the hand-crafted one. PEG seems like a great tool for 
 tasks where maximum performance isn’t as important.

  — John

 On Jul 4, 2014, at 11:09 AM, Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 I got sidetracked by a couple of other things, but the parser is now 
 updated with a bunch of bug fixes. I have a preliminary CSV and graphdot 
 parser (very reduced from the full grammar). I'm starting to put together 
 some more comprehensive tests together.

 As for speed comparison to DataFrames for parsing CSV it's much slower. 
 I've spent time trying to optimize things, but I suspect a large part of 
 the speed issue is the overhead of function calls. Also, I suspect it will 
 be hard to come close to the speed of DataFrames as the code looks like 
 it's fairly optimized for reading just CSV files.

 After a few more tests are written, I'm getting ready to officially call a 
 version 0.1.

 On Thursday, June 5, 2014 6:56:37 AM UTC-4, Abe Schneider wrote:

 I also forgot to push the changes last night.

 On Wednesday, June 4, 2014 11:01:33 PM UTC-4, Abe Schneider wrote:

 After playing around with a bunch of alternatives, I think I've come up 
 with decent action semantics:

 @transform name begin
  label = action
 end

 For example, a simple graph grammar might look like:

 @grammar nodetest begin
   start = +node_def
   node_def = node_label + node_name + lbrace + data + rbrace
   node_name = string_value + space

   data = *(line + semicolon)
   line = string_value + space
   string_value = r[_a-zA-Z][_a-zA-Z0-9]*

   lbrace = { + space
   rbrace = } + space
   semicolon = ; + space
   node_label = node + space
   space = r[ \t\n]*
 end

 with it's actions to create some data structure:

 type MyNode
   name
   values

   function MyNode(name, values)
 new(name, values)
   end
 end


 with:
 @transform tograph begin
   # ignore these
   lbrace = nothing
   rbrase = nothing
   semicolon = nothing
   node_label = nothing
   space = nothing

   # special action so we don't have to define every label
   default = children

   string_value = node.value
   value = node.value
   line = children
   data = MyNode(, children)
   node_def = begin
 local name = children[1]
 local cnode = children[2]
 cnode.name = name
 return cnode
   end
 end

 and finally, to apply the transform:

 (ast, pos, error) = parse(nodetest, data)
 result = apply(tograph, ast)
 println(result)# {MyNode(foo,{a,b}),MyNode(bar,{c,d})}

 The magic in '@transform' basically just creates the dictionary like 
 before, but automatically wraps the expression on the RHS  as an anonymous 
 function  (node, children) - expr.

 I'm currently looking for a better name than 'children', as it's 
 potentially confusing and misleading. It's actually the values of the child 
 nodes (as opposed to node.children). Maybe cvalues?

 On Sunday, May 25, 2014 10:28:45 PM UTC-4, Abe Schneider wrote:

 I wrote a quick PEG Parser for Julia with Packrat capabilities:

 https://github.com/abeschneider/PEGParser

 It's a first draft and needs a ton of work, testing, etc., but if this 
 is of interest to anyone else, here is a quick description.

 Grammars can be defined using most of the standard EBNF syntax. For 
 example, a simple math grammar can be defined as:

 @grammar mathgrammar begin

   start = expr
   number = r([0-9]+)
   expr = (term + op1 + expr) | term
   term = (factor + op2 + term) | factor
   factor = number | pfactor
   pfactor = ('(' + expr + ')')
   op1 = '+' | '-'
   op2 = '*' | '/'
 end



 To parse a string with the grammar:

 (node, pos, error) = parse(mathgrammar, 5

[julia-users] Re: PEG Parser

2014-07-04 Thread Abe Schneider
I got sidetracked by a couple of other things, but the parser is now 
updated with a bunch of bug fixes. I have a preliminary CSV and graphdot 
parser (very reduced from the full grammar). I'm starting to put together 
some more comprehensive tests together.

As for speed comparison to DataFrames for parsing CSV it's much slower. 
I've spent time trying to optimize things, but I suspect a large part of 
the speed issue is the overhead of function calls. Also, I suspect it will 
be hard to come close to the speed of DataFrames as the code looks like 
it's fairly optimized for reading just CSV files.

After a few more tests are written, I'm getting ready to officially call a 
version 0.1.

On Thursday, June 5, 2014 6:56:37 AM UTC-4, Abe Schneider wrote:

 I also forgot to push the changes last night.

 On Wednesday, June 4, 2014 11:01:33 PM UTC-4, Abe Schneider wrote:

 After playing around with a bunch of alternatives, I think I've come up 
 with decent action semantics:

 @transform name begin
  label = action
 end

 For example, a simple graph grammar might look like:

 @grammar nodetest begin
   start = +node_def
   node_def = node_label + node_name + lbrace + data + rbrace
   node_name = string_value + space

   data = *(line + semicolon)
   line = string_value + space
   string_value = r[_a-zA-Z][_a-zA-Z0-9]*

   lbrace = { + space
   rbrace = } + space
   semicolon = ; + space
   node_label = node + space
   space = r[ \t\n]*
 end

 with it's actions to create some data structure:

 type MyNode
   name
   values

   function MyNode(name, values)
 new(name, values)
   end
 end


 with:
 @transform tograph begin
   # ignore these
   lbrace = nothing
   rbrase = nothing
   semicolon = nothing
   node_label = nothing
   space = nothing

   # special action so we don't have to define every label
   default = children

   string_value = node.value
   value = node.value
   line = children
   data = MyNode(, children)
   node_def = begin
 local name = children[1]
 local cnode = children[2]
 cnode.name = name
 return cnode
   end
 end

 and finally, to apply the transform:

 (ast, pos, error) = parse(nodetest, data)
 result = apply(tograph, ast)
 println(result)# {MyNode(foo,{a,b}),MyNode(bar,{c,d})}

 The magic in '@transform' basically just creates the dictionary like 
 before, but automatically wraps the expression on the RHS  as an anonymous 
 function  (node, children) - expr.

 I'm currently looking for a better name than 'children', as it's 
 potentially confusing and misleading. It's actually the values of the child 
 nodes (as opposed to node.children). Maybe cvalues?

 On Sunday, May 25, 2014 10:28:45 PM UTC-4, Abe Schneider wrote:

 I wrote a quick PEG Parser for Julia with Packrat capabilities:

 https://github.com/abeschneider/PEGParser

 It's a first draft and needs a ton of work, testing, etc., but if this 
 is of interest to anyone else, here is a quick description.

 Grammars can be defined using most of the standard EBNF syntax. For 
 example, a simple math grammar can be defined as:

 @grammar mathgrammar begin

   start = expr
   number = r([0-9]+)
   expr = (term + op1 + expr) | term
   term = (factor + op2 + term) | factor
   factor = number | pfactor
   pfactor = ('(' + expr + ')')
   op1 = '+' | '-'
   op2 = '*' | '/'
 end



 To parse a string with the grammar:

 (node, pos, error) = parse(mathgrammar, 5*(2-6))

 This will create an AST which can then be transformed to a value. 
 Currently this is accomplished by doing:

 math = Dict()

 math[number] = (node, children) - float(node.value)
 math[expr] = (node, children) -
 length(children) == 1 ? children : eval(Expr(:call, children[2], 
 children[1], children[3]))
 math[factor] = (node, children) - children
 math[pfactor] = (node, children) - children[2]
 math[term] = (node, children) -
 length(children) == 1 ? children : eval(Expr(:call, children[2], 
 children[1], children[3]))
 math[op1] = (node, children) - symbol(node.value)
 math[op2] = (node, children) - symbol(node.value)


 Ideally, I would like to simplify this to using multi-dispatch on 
 symbols (see previous post), but for now this is the easiest way to define 
 actions based on node attributes.

 Finally, to transform the tree:

 result = transform(math, node)  # will give the value of 20

 Originally I was going to attach the transforms to the rules themselves 
 (similiar to boost::spirit). However, there were two reasons for not doing 
 this:

1. To implement the packrat part of the parser, I needed to cache 
the results which meant building an AST anyways
2. It's nice to be apply to get different transforms for the same 
grammar (e.g. you may want to transform the result into HTML, LaTeX, 
 etc.)

 The downside of the separation is that it adds some more complexity to 
 the process.



Re: [julia-users] type design question

2014-06-22 Thread Abe Schneider
Out of curiosity, what is wrong with Scala's method to handle this problem 
(where only the concrete types can have constructors)? From the thread you 
linked, it seems like the main complaint against doing so would create a 
stronger coupling between the abstract and concrete types than desired.

However, I think the grouping method suggested above creates the same 
problem. Sure, you can create a layer of abstraction with a getter/setter. 
However, if you're really worried about fields disappearing, the grouping 
method creates more work (you not only change to type, but you have to 
alter the getters/setters).

Also, it seems like the separation between structure and behaviour is 
already broken by having concrete types. Allowing a explicit declaration of 
a structure hierarchy of what you are already doing implicitly with the 
grouping doesn't change the  structure/behaviour relationship to me. If you 
couldn't group and if there weren't concrete types, then I would have to 
agree with you.

Thanks for listening!

On Saturday, June 21, 2014 11:35:53 AM UTC-4, Stefan Karpinski wrote:

 In particular, I think the constructor issue cuts to the heart of the 
 matter. If you have any good thoughts on that, it might help revive that 
 discussion. So far the best proposal for subtype construction in the 
 presence of abstract types with fields basically leads you to the parent 
 structure as leading field pattern that's been suggested here.

 On Jun 21, 2014, at 11:23 AM, Stefan Karpinski stefan.k...@gmail.com 
 javascript: wrote:

 It's non-orthogonal because subtyping becomes about sharing both behavior 
 and structure, not just behavior. An orthogonal approach would use an 
 independent feature for sharing structure. This is all covered in the 
 discussion in https://github.com/JuliaLang/julia/issues/4935.

 On Jun 21, 2014, at 9:59 AM, Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 I think that's a fair point (though I may disagree that it's 
 non-othogonal). My main point is that you are already implicitly using a 
 hierarchical structure with grouping. Therefore, I don't see this as adding 
 a new feature to the language, it's already something you can do in Julia, 
 but rather providing the syntax to allow the relationship to be declared in 
 useful way.

 The code:
 abstract A
   x::Int64
 end

 type B : A
   y::Int64
 end

 type C : A
   z::Float64
 end


 is much clearer to me than:
 type A
   int x::Int64
 end

 abstract AType
 getx(a::AType) = a.x
 setx(a::AType, x::Int64) = a.x = x

 type B : AType
   parent::A
 end

 type C : AType
   parent::C
 end


 or:
 abstract A

 type B : A
   x::Int64
   y::Int64
 end

 type C : A
   x::Int64
   z::Float64
 end


 The last two examples violate DRY, make for potentially difficult to 
 maintain code, and are less obvious to someone else looking at the code as 
 to what is happening.

 On Saturday, June 21, 2014 9:02:52 AM UTC-4, Stefan Karpinski wrote:

 The harm is adding unnecessary, non-orthogonal language features. We've 
 tended not to add features until it becomes very clear that we need them 
 and why, and that's been a good approach so far. Aside from several 
 discussions similar to this, I don't feel like the problems this feature 
 would alleviate are especially pressing. So far subtyping in Julia is 
 purely about behavior, not structure and changing that even a little bit 
 would require some significant motivation – certainly more than why not?

 On Jun 21, 2014, at 8:45 AM, Abe Schneider abe.sc...@gmail.com wrote:

 After some thought, it occurred to me that with the grouping you 
 suggested, you are really implementing a type of inheritance. If you rename 
 your sub-type as 'parent' you have:

 type ParentClass
   # vars
 end

 abstract ParentClassType

 type ChildClass : ParentClassType
   parent::ParentClass
   # vars
 end

 which is exactly what a Mixin paradigm would accomplish, only that the 
 compiler would help with the construction (which at the end of the day is 
 all OOP really is). If this type of construction can be done by hand, I'm 
 not sure what the harm is in having the compiler make things easier.

 On Saturday, June 21, 2014 3:09:36 AM UTC-4, Tobias Knopp wrote:

 When I switched from C++ to C# I had a similar opinion about the issue 
 of duplicated fields in all classes implementing an interface. But when 
 getting used to grouping things together and using has-a relations this has 
 changed my thinking about it.
 I now think that it enforces structuring code in a sane way. When 
 inheriting field members one often observes far to late that one has 
 structural issues and refactoring then becomes really hard.

 When looking at Julia base code (or several of the packages) one will 
 see that the issue of inheriting field members does not come up so much.

 One side comment. In Julia the possibility to use duck typing gives a 
 lot of flexibility. And when one reaches limits (e.g. due to the absence

Re: [julia-users] type design question

2014-06-21 Thread Abe Schneider
After some thought, it occurred to me that with the grouping you suggested, 
you are really implementing a type of inheritance. If you rename your 
sub-type as 'parent' you have:

type ParentClass
  # vars
end

abstract ParentClassType

type ChildClass : ParentClassType
  parent::ParentClass
  # vars
end

which is exactly what a Mixin paradigm would accomplish, only that the 
compiler would help with the construction (which at the end of the day is 
all OOP really is). If this type of construction can be done by hand, I'm 
not sure what the harm is in having the compiler make things easier.

On Saturday, June 21, 2014 3:09:36 AM UTC-4, Tobias Knopp wrote:

 When I switched from C++ to C# I had a similar opinion about the issue of 
 duplicated fields in all classes implementing an interface. But when 
 getting used to grouping things together and using has-a relations this has 
 changed my thinking about it.
 I now think that it enforces structuring code in a sane way. When 
 inheriting field members one often observes far to late that one has 
 structural issues and refactoring then becomes really hard.

 When looking at Julia base code (or several of the packages) one will see 
 that the issue of inheriting field members does not come up so much.

 One side comment. In Julia the possibility to use duck typing gives a lot 
 of flexibility. And when one reaches limits (e.g. due to the absence of 
 abstract multiple inheritance) duck typing is often a solution.

 Am Samstag, 21. Juni 2014 03:43:57 UTC+2 schrieb Abe Schneider:

 I agree, I think it's the best solution given the tools (and what I'm 
 going to use for my code). However, it still feels more like a hack around 
 the design than good programming practice.

 On Friday, June 20, 2014 5:41:02 PM UTC-4, Spencer Russell wrote:

 I'd just like to second Jameson's suggestion of aggregating the common 
 fields into a type that all your subclasses contain.

 I did quite a bit of thinking on this issue when it came up in AudioIO, 
 and was lucky enough to have both Jeff and Stefan around to bounce ideas 
 off of.

 My main issues with the duplicated data in subclasses were:

1. It's annoying to have to add the same set of fields every time 
you define a subtype, and violates DRY. It's also error prone. 
2. If you want to add a feature to the base type that requires a new 
field, EVERYONE WHO EVER SUBTYPED your base type now has to add the 
 field 
to their subtype. It's bad enough when this is within your own codebase, 
but if there's other code subtyping it then you're really in trouble. 

 Encapsulating the common fields solves both those issues.If you want to 
 add new fields later on you can just add them to the aggregating type. Most 
 importantly, it does it in really easy-to-reason-about way, without adding 
 any tricky edge cases or complicated rules for developers to understand.

 peace,
 s


 On Fri, Jun 20, 2014 at 3:57 PM, Abe Schneider abe.sc...@gmail.com 
 wrote:

 I was thinking something along those lines, but as was pointed out, you 
 would have to also create the constructors.

 Unfortunately, I'm on my phone right now, so I can't effectively post 
 code. I was thinking of a 'mixin' macro which would create a new type 
 (with 
 constructor):

 @mixin Foo : Bar Baz

 Would create Foo from both Bar and Baz. However, because there is no 
 MI, you could only inherit from Bar.

 While it does have some magic to it, it might not be awful. Also, you 
 could still make an outer constructor for it.

 Of course, I don't know the actual technical challenges to making it, 
 since I haven't had time to write any code.




Re: [julia-users] type design question

2014-06-21 Thread Abe Schneider
I think that's a fair point (though I may disagree that it's 
non-othogonal). My main point is that you are already implicitly using a 
hierarchical structure with grouping. Therefore, I don't see this as adding 
a new feature to the language, it's already something you can do in Julia, 
but rather providing the syntax to allow the relationship to be declared in 
useful way.

The code:
abstract A
  x::Int64
end

type B : A
  y::Int64
end

type C : A
  z::Float64
end


is much clearer to me than:
type A
  int x::Int64
end

abstract AType
getx(a::AType) = a.x
setx(a::AType, x::Int64) = a.x = x

type B : AType
  parent::A
end

type C : AType
  parent::C
end


or:
abstract A

type B : A
  x::Int64
  y::Int64
end

type C : A
  x::Int64
  z::Float64
end


The last two examples violate DRY, make for potentially difficult to 
maintain code, and are less obvious to someone else looking at the code as 
to what is happening.

On Saturday, June 21, 2014 9:02:52 AM UTC-4, Stefan Karpinski wrote:

 The harm is adding unnecessary, non-orthogonal language features. We've 
 tended not to add features until it becomes very clear that we need them 
 and why, and that's been a good approach so far. Aside from several 
 discussions similar to this, I don't feel like the problems this feature 
 would alleviate are especially pressing. So far subtyping in Julia is 
 purely about behavior, not structure and changing that even a little bit 
 would require some significant motivation – certainly more than why not?

 On Jun 21, 2014, at 8:45 AM, Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 After some thought, it occurred to me that with the grouping you 
 suggested, you are really implementing a type of inheritance. If you rename 
 your sub-type as 'parent' you have:

 type ParentClass
   # vars
 end

 abstract ParentClassType

 type ChildClass : ParentClassType
   parent::ParentClass
   # vars
 end

 which is exactly what a Mixin paradigm would accomplish, only that the 
 compiler would help with the construction (which at the end of the day is 
 all OOP really is). If this type of construction can be done by hand, I'm 
 not sure what the harm is in having the compiler make things easier.

 On Saturday, June 21, 2014 3:09:36 AM UTC-4, Tobias Knopp wrote:

 When I switched from C++ to C# I had a similar opinion about the issue of 
 duplicated fields in all classes implementing an interface. But when 
 getting used to grouping things together and using has-a relations this has 
 changed my thinking about it.
 I now think that it enforces structuring code in a sane way. When 
 inheriting field members one often observes far to late that one has 
 structural issues and refactoring then becomes really hard.

 When looking at Julia base code (or several of the packages) one will see 
 that the issue of inheriting field members does not come up so much.

 One side comment. In Julia the possibility to use duck typing gives a lot 
 of flexibility. And when one reaches limits (e.g. due to the absence of 
 abstract multiple inheritance) duck typing is often a solution.

 Am Samstag, 21. Juni 2014 03:43:57 UTC+2 schrieb Abe Schneider:

 I agree, I think it's the best solution given the tools (and what I'm 
 going to use for my code). However, it still feels more like a hack around 
 the design than good programming practice.

 On Friday, June 20, 2014 5:41:02 PM UTC-4, Spencer Russell wrote:

 I'd just like to second Jameson's suggestion of aggregating the common 
 fields into a type that all your subclasses contain.

 I did quite a bit of thinking on this issue when it came up in AudioIO, 
 and was lucky enough to have both Jeff and Stefan around to bounce ideas 
 off of.

 My main issues with the duplicated data in subclasses were:

1. It's annoying to have to add the same set of fields every time 
you define a subtype, and violates DRY. It's also error prone. 
2. If you want to add a feature to the base type that requires a 
new field, EVERYONE WHO EVER SUBTYPED your base type now has to add the 
field to their subtype. It's bad enough when this is within your own 
codebase, but if there's other code subtyping it then you're really in 
trouble. 

 Encapsulating the common fields solves both those issues.If you want to 
 add new fields later on you can just add them to the aggregating type. 
 Most 
 importantly, it does it in really easy-to-reason-about way, without adding 
 any tricky edge cases or complicated rules for developers to understand.

 peace,
 s


 On Fri, Jun 20, 2014 at 3:57 PM, Abe Schneider abe.sc...@gmail.com 
 wrote:

 I was thinking something along those lines, but as was pointed out, 
 you would have to also create the constructors.

 Unfortunately, I'm on my phone right now, so I can't effectively post 
 code. I was thinking of a 'mixin' macro which would create a new type 
 (with 
 constructor):

 @mixin Foo : Bar Baz

 Would create Foo from both Bar and Baz. However, because

Re: [julia-users] type design question

2014-06-20 Thread Abe Schneider
Thanks for the links!

My main complaint with declaring the variables rather than defining the 
interface. I was never a fan of Java interfaces, which I think is 
essentially what the current Julia design already mimics (if not in a 
slightly less formal design). Having to redeclare variables for larger 
projects can become difficult for the programmer who might have to visit 
each of the interfaces defined to see which variables are expected to be 
exported. If you only allow for a single interface to be defined, you are 
saved some work, but at the expense of design (I can think of many 
instances where multiple instances are desirable).

I think allowing abstract types to declare variables solves most of this 
problem. I can appreciate people's reserve on implementing 
multiple-inheritance. As another data point, most modern languages seem to 
using Mixins instead (e.g.: Java 8, Scala, Ruby, Swift). Java 8 is 
especially interesting as they started off with the same interface design.

In Scala (if my memory serves me correctly), Mixins are enabled by having a 
separate structure-type called traits. What distinguishes classes from 
traits is that classes are allowed constructors whereas traits are not. 
This eliminates most of the problems people have with implementing multiple 
inheritance.

Obviously, it's possible to design the NNModules with the current feature 
set of Julia. However, at least to me, it won't feel like a good design if 
I have to repeat the same fields for all children of NNModules (there is 
more than just output). It also makes me worry as to how well Julia will 
scale for larger projects, though the answer may be that is not it's main 
use.


On Friday, June 20, 2014 2:30:04 AM UTC-4, Tobias Knopp wrote:

 Hi Abe,

 There has been various discussions about this in the following threads:

 https://github.com/JuliaLang/julia/issues/4935
 https://github.com/JuliaLang/julia/issues/1974

 You might see that there is not yet a consus if one of these features will 
 be implemented or not.

 I have been myself trying to figure out how to resolve the issue of 
 duplicating code until Jeff and Tim showed me the solution Jameson has 
 outlined above.
 I don't really see why solution is too verbose. You only have to define 
 the getter function for public types where it is encouraged anyway to 
 define functions for data encapsulation. Fields are in the current view 
 private. 

 You might be also interested in 
 https://github.com/JuliaLang/julia/issues/6975 where we discuss how to 
 define interfaces more formally as it is done now.

 Cheers,

 Tobi

 Am Freitag, 20. Juni 2014 04:15:21 UTC+2 schrieb Abe Schneider:

 Okay, so that matches the Java interface style, where you would then make 
 one function per variable you want to officially sanction as required.

 One thing I didn't except from doing this is that if you do:
 type OtherModule : NNModule end

 mod = OtherModule
 getoutput(mod)

 I was expecting an error within the method that 'output' doesn't exist 
 for 'mod'. Instead I get:
 ERROR: no method getoutput(Type{OtherModule})

 which is a much nicer complaint.


 The downside of the design is that now I have to duplicate the variable 
 for every type, but also make sure there's a function defined at top. 
 However, of the choices to make, it's probably the cleanest (though a macro 
 might save a little on typing).

 Thanks for the help!



 On Thursday, June 19, 2014 9:14:34 AM UTC-4, Jameson wrote:

 here is my recommended solution:


 abstract NNModule
 getoutput(nnm::NNModule) = nnm.output # -- add this line

 type LinearModule : NNModule
   weight::Array{Float64}
   output::Array{Float64}
 end

 type SigmoidModule : NNModule
   output::Array{Float64}
 end


 On Thu, Jun 19, 2014 at 8:18 AM, Abe Schneider abe.sc...@gmail.com 
 wrote:

 I'm trying to figure out the best way to factor code that consists of 
 repeated modules which all share some common attributes.

 Specifically, if I have (very abbreviated from actual code):

 abstract NNModule

 type LinearModule : NNModule
   weight::Array{Float64}
   output::Array{Float64}
 end

 type SigmoidModule : NNModule
   output::Array{Float64}
 end

 For both modules I need an 'output' variable. I know the idea of 
 putting variables in an abstract type has come up before. However, while 
 it 
 would solve this problem, it is also not yet resolved (and may or may not 
 actually happy).

 Given that, two alternatives occur to me:
 1. Keep the current design and be okay with repeated code (difficult)
 2. Use a macro to create the repeated code for me

 Option (1) is certainly the easiest, and probably the one I'll stick 
 with for now. However, it seems error prone and (IMHO) produces ugly code.

 Option (2) has the problem that it can make what's actually happening 
 opaque and could potentially produce bugs that are difficult to track down.

 So my questions are: 
 (1) Have other people come across design issues like this before

Re: [julia-users] type design question

2014-06-20 Thread Abe Schneider
It's good to see other people want multiple inheritance too :).

One thing I haven't seen discussion yet is using Scala's method of constructors 
to make deal with the fields and MI.

It seems like abstract types could be equivalent to Scala traits (if abstract 
types allowed fields), and regular types to classes.

Abstract types wouldn't be allowed constructors (like traits), and thus the 
regular types would have complete control as how to initialize the variables.

Thus, in Julia the main difference between the two would be whether a 
constructor exists (in keeping with their name).

I generally agree with not wanting deep hierarchies. However, as it stands, it 
seems like even shallow hierarchies are difficult.

I also think it's languages like Java that tend to create the large hierarchies 
because it doesn't have multiple inheritance of mixins. Generally in c++ things 
tend to be fairly shallow.


Re: [julia-users] type design question

2014-06-20 Thread Abe Schneider
I was thinking something along those lines, but as was pointed out, you would 
have to also create the constructors.

Unfortunately, I'm on my phone right now, so I can't effectively post code. I 
was thinking of a 'mixin' macro which would create a new type (with 
constructor):

@mixin Foo : Bar Baz

Would create Foo from both Bar and Baz. However, because there is no MI, you 
could only inherit from Bar.

While it does have some magic to it, it might not be awful. Also, you could 
still make an outer constructor for it.

Of course, I don't know the actual technical challenges to making it, since I 
haven't had time to write any code.


Re: [julia-users] type design question

2014-06-20 Thread Abe Schneider
I was thinking something along those lines, but as was pointed out, you would 
have to also create the constructors.

Unfortunately, I'm on my phone right now, so I can't effectively post code. I 
was thinking of a 'mixin' macro which would create a new type (with 
constructor):

@mixin Foo : Bar Baz

Would create Foo from both Bar and Baz. However, because there is no MI, you 
could only inherit from Bar.

While it does have some magic to it, it might not be awful. Also, you could 
still make an outer constructor for it.

Of course, I don't know the actual technical challenges to making it, since I 
haven't had time to write any code.


Re: [julia-users] type design question

2014-06-20 Thread Abe Schneider
I agree, I think it's the best solution given the tools (and what I'm going 
to use for my code). However, it still feels more like a hack around the 
design than good programming practice.

On Friday, June 20, 2014 5:41:02 PM UTC-4, Spencer Russell wrote:

 I'd just like to second Jameson's suggestion of aggregating the common 
 fields into a type that all your subclasses contain.

 I did quite a bit of thinking on this issue when it came up in AudioIO, 
 and was lucky enough to have both Jeff and Stefan around to bounce ideas 
 off of.

 My main issues with the duplicated data in subclasses were:

1. It's annoying to have to add the same set of fields every time you 
define a subtype, and violates DRY. It's also error prone. 
2. If you want to add a feature to the base type that requires a new 
field, EVERYONE WHO EVER SUBTYPED your base type now has to add the field 
to their subtype. It's bad enough when this is within your own codebase, 
but if there's other code subtyping it then you're really in trouble. 

 Encapsulating the common fields solves both those issues.If you want to 
 add new fields later on you can just add them to the aggregating type. Most 
 importantly, it does it in really easy-to-reason-about way, without adding 
 any tricky edge cases or complicated rules for developers to understand.

 peace,
 s


 On Fri, Jun 20, 2014 at 3:57 PM, Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 I was thinking something along those lines, but as was pointed out, you 
 would have to also create the constructors.

 Unfortunately, I'm on my phone right now, so I can't effectively post 
 code. I was thinking of a 'mixin' macro which would create a new type (with 
 constructor):

 @mixin Foo : Bar Baz

 Would create Foo from both Bar and Baz. However, because there is no MI, 
 you could only inherit from Bar.

 While it does have some magic to it, it might not be awful. Also, you 
 could still make an outer constructor for it.

 Of course, I don't know the actual technical challenges to making it, 
 since I haven't had time to write any code.




[julia-users] type design question

2014-06-19 Thread Abe Schneider
I'm trying to figure out the best way to factor code that consists of 
repeated modules which all share some common attributes.

Specifically, if I have (very abbreviated from actual code):

abstract NNModule

type LinearModule : NNModule
  weight::Array{Float64}
  output::Array{Float64}
end

type SigmoidModule : NNModule
  output::Array{Float64}
end

For both modules I need an 'output' variable. I know the idea of putting 
variables in an abstract type has come up before. However, while it would 
solve this problem, it is also not yet resolved (and may or may not 
actually happy).

Given that, two alternatives occur to me:
1. Keep the current design and be okay with repeated code (difficult)
2. Use a macro to create the repeated code for me

Option (1) is certainly the easiest, and probably the one I'll stick with 
for now. However, it seems error prone and (IMHO) produces ugly code.

Option (2) has the problem that it can make what's actually happening 
opaque and could potentially produce bugs that are difficult to track down.

So my questions are: 
(1) Have other people come across design issues like this before, and how 
did they deal with it?
(2) Is there a macro out there already to accomplish this? After a quick 
search, I found '@delegate' proposed as a solution for something like this, 
but it was never officially merged. If not, any suggestions on how such a 
macro should act/look?


As a side note, it would be great if Julia added properties to abstract 
types. The current design gives something equivalent to Java's interfaces, 
where most languages opt for mixins instead.

Thanks!


Re: [julia-users] type design question

2014-06-19 Thread Abe Schneider
Okay, so that matches the Java interface style, where you would then make 
one function per variable you want to officially sanction as required.

One thing I didn't except from doing this is that if you do:
type OtherModule : NNModule end

mod = OtherModule
getoutput(mod)

I was expecting an error within the method that 'output' doesn't exist for 
'mod'. Instead I get:
ERROR: no method getoutput(Type{OtherModule})

which is a much nicer complaint.


The downside of the design is that now I have to duplicate the variable for 
every type, but also make sure there's a function defined at top. However, 
of the choices to make, it's probably the cleanest (though a macro might 
save a little on typing).

Thanks for the help!



On Thursday, June 19, 2014 9:14:34 AM UTC-4, Jameson wrote:

 here is my recommended solution:


 abstract NNModule
 getoutput(nnm::NNModule) = nnm.output # -- add this line

 type LinearModule : NNModule
   weight::Array{Float64}
   output::Array{Float64}
 end

 type SigmoidModule : NNModule
   output::Array{Float64}
 end


 On Thu, Jun 19, 2014 at 8:18 AM, Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 I'm trying to figure out the best way to factor code that consists of 
 repeated modules which all share some common attributes.

 Specifically, if I have (very abbreviated from actual code):

 abstract NNModule

 type LinearModule : NNModule
   weight::Array{Float64}
   output::Array{Float64}
 end

 type SigmoidModule : NNModule
   output::Array{Float64}
 end

 For both modules I need an 'output' variable. I know the idea of putting 
 variables in an abstract type has come up before. However, while it would 
 solve this problem, it is also not yet resolved (and may or may not 
 actually happy).

 Given that, two alternatives occur to me:
 1. Keep the current design and be okay with repeated code (difficult)
 2. Use a macro to create the repeated code for me

 Option (1) is certainly the easiest, and probably the one I'll stick with 
 for now. However, it seems error prone and (IMHO) produces ugly code.

 Option (2) has the problem that it can make what's actually happening 
 opaque and could potentially produce bugs that are difficult to track down.

 So my questions are: 
 (1) Have other people come across design issues like this before, and how 
 did they deal with it?
 (2) Is there a macro out there already to accomplish this? After a quick 
 search, I found '@delegate' proposed as a solution for something like this, 
 but it was never officially merged. If not, any suggestions on how such a 
 macro should act/look?


 As a side note, it would be great if Julia added properties to abstract 
 types. The current design gives something equivalent to Java's interfaces, 
 where most languages opt for mixins instead.

 Thanks!




Re: [julia-users] animation using Gtk+/Cairo

2014-06-17 Thread Abe Schneider
Thank you everyone for the fast replies!

After looking at ImageView and the sources, here's the solution I came up 
with:

w = Gtk.@Window() |
(body=Gtk.@Box(:v) |
  (canvas=Gtk.@Canvas(600, 600)) |
showall

function redraw_canvas(canvas)
  ctx = getgc(canvas)
  h = height(canvas)
  w = width(canvas)

  # draw background
  rectangle(ctx, 0, 0, w, h)
  set_source_rgb(ctx, 1, 1, 1)
  fill(ctx)

  # draw objects
  # ...

  # tell Gtk+ to redisplay
  draw(canvas)
end

function init(canvas, delay::Float64, interval::Float64)
  update_timer = Timer(timer - redraw_canvas(canvas))
  start_timer(update_timer, delay, interval)
end

update_timer = init(canvas, 2, 1)
if !isinteractive()
  wait(Condition())
end

stop_timer(update_timer)

I haven't looked yet into what is required to do double-buffering (or if 
it's enabled by default). I also copied the 'wait(Condition())' from the 
docs, though it's not clear to me what the condition is (if I close the 
window, the program is still running -- I'm assuming that means I need to 
connect the signal for window destruction to said condition).

A

On Monday, June 16, 2014 9:33:42 PM UTC-4, Jameson wrote:

 I would definately use Julia's timers. See `Gtk.jl/src/cairo.jl` for an 
 example interface to the Cairo backing to a Gtk window (used in 
 `Winston.jl/src/gtk.jl`). If you are using this wrapper, call `draw(w)` to 
 force a redraw immediately, or `draw(w,false)` to queue a redraw request 
 for when Gtk is idle.


 On Mon, Jun 16, 2014 at 9:12 PM, Tim Holy tim@gmail.com javascript:
  wrote:

 ImageView's navigation.jl contains an example. The default branch is Tk
 (because  as far as binary distribution goes, Tk is solved and Gtk isn't
 yet), but it has a gtk branch you can look at.

 --Tim

 On Monday, June 16, 2014 04:01:46 PM Abe Schneider wrote:
  I was looking for a way to display a simulation in Julia. Originally I 
 was
  going to just use PyPlot, but it occurred to me it would be better to 
 just
  use Gtk+ + Cairo to do the drawing rather than something whose main 
 purpose
  is drawing graphs.
 
  So far, following the examples on the Github page, I have no problem
  creating a window with a Cairo canvas. I can also display content on the
  canvas fairly easily (which speaks volumes on the awesomeness of Julia 
 and
  the Gtk+ library). However, after looking through the code and samples,
  it's not obvious to me how to redraw the canvas every fraction of a 
 second
  to display new content.
 
  I did find an example of animating with Cairo and Gtk+ in C
  (http://cairographics.org/threaded_animation_with_cairo/). However, I
  assume one would want to use Julia's timers instead of of GLibs? 
 Secondly,
  there in their function 'timer_exe', call is made directly to Gtk+ to 
 send
  a redraw queue to the window. Is there a cleaner way to do it with the 
 Gtk+
  library?
 
  Thanks!
  A




Re: [julia-users] animation using Gtk+/Cairo

2014-06-17 Thread Abe Schneider
@Tim: Awesome, exactly what I was looking for. Thank you.

@Jameson: Just to check, do you mean something like:

function redraw_canvas(canvas)
  draw(canvas)
end

draw(canvas) do widget
  # ...
end

If so, I'll re-post my code with the update. It may be useful to someone 
else to see the entire code as an example.

Thanks!
A


On Tuesday, June 17, 2014 10:44:16 AM UTC-4, Jameson wrote:

 This code is not valid, since getgc does not always have a valid drawing 
 context to return. Instead you need to provide Canvas with a callback 
 function via a call to redraw in which you do all the work, then just call 
 draw(canvas) in your timer callback to force an update to the view. 
 double-buffering is enabled by default.

 wait(Condition()) is the same wait(), and means sleep until this task is 
 signaled, and thereby prevents the program from exiting early


 On Tue, Jun 17, 2014 at 7:46 AM, Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 Thank you everyone for the fast replies!

 After looking at ImageView and the sources, here's the solution I came up 
 with:

 w = Gtk.@Window() |
 (body=Gtk.@Box(:v) |
   (canvas=Gtk.@Canvas(600, 600)) |
 showall

 function redraw_canvas(canvas)
   ctx = getgc(canvas)
   h = height(canvas)
   w = width(canvas)

   # draw background
   rectangle(ctx, 0, 0, w, h)
   set_source_rgb(ctx, 1, 1, 1)
   fill(ctx)

   # draw objects
   # ...

   # tell Gtk+ to redisplay
   draw(canvas)
 end

 function init(canvas, delay::Float64, interval::Float64)
   update_timer = Timer(timer - redraw_canvas(canvas))
   start_timer(update_timer, delay, interval)
 end

 update_timer = init(canvas, 2, 1)
 if !isinteractive()
   wait(Condition())
 end

 stop_timer(update_timer)

 I haven't looked yet into what is required to do double-buffering (or if 
 it's enabled by default). I also copied the 'wait(Condition())' from the 
 docs, though it's not clear to me what the condition is (if I close the 
 window, the program is still running -- I'm assuming that means I need to 
 connect the signal for window destruction to said condition).

 A


 On Monday, June 16, 2014 9:33:42 PM UTC-4, Jameson wrote:

 I would definately use Julia's timers. See `Gtk.jl/src/cairo.jl` for an 
 example interface to the Cairo backing to a Gtk window (used in 
 `Winston.jl/src/gtk.jl`). If you are using this wrapper, call `draw(w)` to 
 force a redraw immediately, or `draw(w,false)` to queue a redraw request 
 for when Gtk is idle.


 On Mon, Jun 16, 2014 at 9:12 PM, Tim Holy tim@gmail.com wrote:

 ImageView's navigation.jl contains an example. The default branch is Tk
 (because  as far as binary distribution goes, Tk is solved and Gtk 
 isn't
 yet), but it has a gtk branch you can look at.

 --Tim

 On Monday, June 16, 2014 04:01:46 PM Abe Schneider wrote:
  I was looking for a way to display a simulation in Julia. Originally 
 I was
  going to just use PyPlot, but it occurred to me it would be better to 
 just
  use Gtk+ + Cairo to do the drawing rather than something whose main 
 purpose
  is drawing graphs.
 
  So far, following the examples on the Github page, I have no problem
  creating a window with a Cairo canvas. I can also display content on 
 the
  canvas fairly easily (which speaks volumes on the awesomeness of 
 Julia and
  the Gtk+ library). However, after looking through the code and 
 samples,
  it's not obvious to me how to redraw the canvas every fraction of a 
 second
  to display new content.
 
  I did find an example of animating with Cairo and Gtk+ in C
  (http://cairographics.org/threaded_animation_with_cairo/). However, I
  assume one would want to use Julia's timers instead of of GLibs? 
 Secondly,
  there in their function 'timer_exe', call is made directly to Gtk+ to 
 send
  a redraw queue to the window. Is there a cleaner way to do it with 
 the Gtk+
  library?
 
  Thanks!
  A





Re: [julia-users] animation using Gtk+/Cairo

2014-06-17 Thread Abe Schneider
Okay, what works for me using your suggestion (except for me [with a 1 day 
old Julia and package] it's 'draw' and not 'redraw'), I have:

function update(canvas, scene::Scene)
  # update scene
  # ...
  
  # redraw
  draw(canvas)
end

function init(canvas, scene::Scene)
  update_timer = Timer(timer - update(canvas, scene))
  start_timer(update_timer, 1, 0.5)
  return update_timer
end

function draw_scene(canvas, scene::Scene)
  ctx = getgc(canvas)
  h = height(canvas)
  w = width(canvas)

  rectangle(ctx, 0, 0, w, h)
  set_source_rgb(ctx, 1, 1, 1)
  fill(ctx)

  # use scene to draw other elements
  # ...
end

scene = Scene(...)
update_timer = init(canvas, scene)
draw(canvas - draw_scene(canvas, scene), canvas)

if !isinteractive()
  cond = Condition()
  signal_connect(win, :destroy) do widget
notify(cond)
  end

  wait(cond)
end

stop_timer(update_timer)


I wasn't sure if the way I bound the scene to the redraw is the nicest 
approach to take. If the function took additional parameters, that seems 
like it might be the most straight forward. E.g.:

draw(canvas, scene) do widget
   # ...
end

# here 'myscene' would be passed as the second parameter to the other draw
draw(canvas, myscene)


A

On Tuesday, June 17, 2014 1:16:11 PM UTC-4, Jameson wrote:

 Yes. Although I think the draw...do function is actually redraw...do 
 (this is actually a shared interface with Tk.jl, although I recommend Gtk :)

 Sent from my phone. 

 On Tuesday, June 17, 2014, Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 @Tim: Awesome, exactly what I was looking for. Thank you.

 @Jameson: Just to check, do you mean something like:

 function redraw_canvas(canvas)
   draw(canvas)
 end

 draw(canvas) do widget
   # ...
 end

 If so, I'll re-post my code with the update. It may be useful to someone 
 else to see the entire code as an example.

 Thanks!
 A


 On Tuesday, June 17, 2014 10:44:16 AM UTC-4, Jameson wrote:

 This code is not valid, since getgc does not always have a valid drawing 
 context to return. Instead you need to provide Canvas with a callback 
 function via a call to redraw in which you do all the work, then just call 
 draw(canvas) in your timer callback to force an update to the view. 
 double-buffering is enabled by default.

 wait(Condition()) is the same wait(), and means sleep until this task is 
 signaled, and thereby prevents the program from exiting early


 On Tue, Jun 17, 2014 at 7:46 AM, Abe Schneider abe.sc...@gmail.com 
 wrote:

 Thank you everyone for the fast replies!

 After looking at ImageView and the sources, here's the solution I came 
 up with:

 w = Gtk.@Window() |
 (body=Gtk.@Box(:v) |
   (canvas=Gtk.@Canvas(600, 600)) |
 showall

 function redraw_canvas(canvas)
   ctx = getgc(canvas)
   h = height(canvas)
   w = width(canvas)

   # draw background
   rectangle(ctx, 0, 0, w, h)
   set_source_rgb(ctx, 1, 1, 1)
   fill(ctx)

   # draw objects
   # ...

   # tell Gtk+ to redisplay
   draw(canvas)
 end

 function init(canvas, delay::Float64, interval::Float64)
   update_timer = Timer(timer - redraw_canvas(canvas))
   start_timer(update_timer, delay, interval)
 end

 update_timer = init(canvas, 2, 1)
 if !isinteractive()
   wait(Condition())
 end

 stop_timer(update_timer)

 I haven't looked yet into what is required to do double-buffering (or 
 if it's enabled by default). I also copied the 'wait(Condition())' from 
 the 
 docs, though it's not clear to me what the condition is (if I close the 
 window, the program is still running -- I'm assuming that means I need to 
 connect the signal for window destruction to said condition).

 A


 On Monday, June 16, 2014 9:33:42 PM UTC-4, Jameson wrote:

 I would definately use Julia's timers. See `Gtk.jl/src/cairo.jl` for 
 an example interface to the Cairo backing to a Gtk window (used in 
 `Winston.jl/src/gtk.jl`). If you are using this wrapper, call `draw(w)` 
 to 
 force a redraw immediately, or `draw(w,false)` to queue a redraw request 
 for when Gtk is idle.


 On Mon, Jun 16, 2014 at 9:12 PM, Tim Holy tim@gmail.com wrote:

 ImageView's navigation.jl contains an example. The default branch is 
 Tk
 (because  as far as binary distribution goes, Tk is solved and Gtk 
 isn't
 yet), but it has a gtk branch you can look at.

 --Tim

 On Monday, June 16, 2014 04:01:46 PM Abe Schneider wrote:
  I was looking for a way to display a simulation in Julia. 
 Originally I was
  going to just use PyPlot, but it occurred to me it would be better 
 to just
  use Gtk+ + Cairo to do the drawing rather than something whose main 
 purpose
  is drawing graphs.
 
  So far, following the examples on the Github page, I have no problem
  creating a window with a Cairo canvas. I can also display content 
 on the
  canvas fairly easily (which speaks volumes on the awesomeness of 
 Julia and
  the Gtk+ library). However, after looking through the code and 
 samples,
  it's not obvious to me how to redraw the canvas every fraction of a 
 second
  to display

[julia-users] animation using Gtk+/Cairo

2014-06-16 Thread Abe Schneider
I was looking for a way to display a simulation in Julia. Originally I was 
going to just use PyPlot, but it occurred to me it would be better to just 
use Gtk+ + Cairo to do the drawing rather than something whose main purpose 
is drawing graphs.

So far, following the examples on the Github page, I have no problem 
creating a window with a Cairo canvas. I can also display content on the 
canvas fairly easily (which speaks volumes on the awesomeness of Julia and 
the Gtk+ library). However, after looking through the code and samples, 
it's not obvious to me how to redraw the canvas every fraction of a second 
to display new content.

I did find an example of animating with Cairo and Gtk+ in C 
(http://cairographics.org/threaded_animation_with_cairo/). However, I 
assume one would want to use Julia's timers instead of of GLibs? Secondly, 
there in their function 'timer_exe', call is made directly to Gtk+ to send 
a redraw queue to the window. Is there a cleaner way to do it with the Gtk+ 
library?

Thanks!
A


Re: [julia-users] Faster sub-strings

2014-06-11 Thread Abe Schneider
Awesome, thanks for the pointer. I'll open up an issue for this.

One thought, it might be nice to have something a little more automatic. 
Specifically, I was thinking if there was an 'ImmutableString' class, you 
would always know that you should make a view rather than a copy. It would 
also be in keeping with the general design where specifying a type allows 
the compiler to do nice optimizations.

On Wednesday, June 11, 2014 9:14:27 AM UTC-4, Kevin Squire wrote:

 Hi Abe,

 Looks like you just reimplemented SubString.

 julia x = Hi there!
 Hi there!

 julia SubString(x, 2, 4)
 i t

 julia typeof(ans)
 SubString{ASCIIString} (constructor with 1 method)


 Which is totally understandable, as there seems to be almost zero 
 documentation about them.  Would you mind opening an issue about that?

 Cheers,
Kevin



 On Wed, Jun 11, 2014 at 5:08 AM, Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 I'm in the middle of profiling my code, and I noticed that I'm paying a 
 penalty for doing a lot of sub-string copies. For what I'm doing, I don't 
 actually need copies of the string, but rather just want to keep a pointer 
 to the string with the range the view occupies. I thought I'd write up a 
 quick test to see if I could speed things up (please ignore the horrible 
 names):

 import Base: getindex, endof, substring

 immutable StringView
   value::String
   first::Int64
   last::Int64
 end

 immutable FastString : String
   value::String
 end

 getindex(s::FastString, r::UnitRange{Int64}) = StringView(s.value, 
 r.start, r.stop)
 endof(s::FastString) = endof(s.value)


 const size = 1000

 function teststring()
   s = randstring(size)
   for i=1:size-10
 value = s[i:(i+10)]
   end
 end

 function teststringview()
   local s::FastString = FastString(randstring(size))
   for i=1:size-10
 value = s[i:(i+10)]
   end
 end

 teststring()
 @time teststring()

 teststringview()
 @time teststringview()


 The results I get are:
 elapsed time: 0.910467582 seconds (890006256 bytes allocated)
 elapsed time: 0.392893967 seconds (40912 bytes allocated)

 The speed-up isn't incredible, but if you're doing a lot of text 
 processing, it might help.

 I'd be curious if anyone had thoughts or better ways of doing this. Or 
 for that matter, reasons why this may be a bad idea.




Re: [julia-users] Faster sub-strings

2014-06-11 Thread Abe Schneider
I think that could also work. I prefer keeping that same syntax for regular 
strings (the square-brackets make things easier to read). I'm assuming 
strings don't normally return views because their contents could change, 
thus copies are safer. That's why I'm suggesting creating an 
'ImmutableString' type. That way you know the contents won't change, and 
returning a view should always be the safe thing to do.

On Wednesday, June 11, 2014 9:45:35 AM UTC-4, gael@gmail.com wrote:

 Hi Abe,

 Looks like you just reimplemented SubString.

 julia x = Hi there!
 Hi there!

 julia SubString(x, 2, 4)
 i t

 julia typeof(ans)
 SubString{ASCIIString} (constructor with 1 method)


 Which is totally understandable, as there seems to be almost zero 
 documentation about them.  Would you mind opening an issue about that?


 Hi both of you.

 Wouldn't it be logical also to have sub handle Strings as it does for 
 arrays?

 julia sub([1,2,3,4,5,6], 1:2)
 2-element SubArray{Int64,1,Array{Int64,1},(UnitRange{Int64},)}:
  1
  2

 and maybe call it view instead of or in addition to sub?



[julia-users] Re: PEG Parser

2014-06-05 Thread Abe Schneider
I also forgot to push the changes last night.

On Wednesday, June 4, 2014 11:01:33 PM UTC-4, Abe Schneider wrote:

 After playing around with a bunch of alternatives, I think I've come up 
 with decent action semantics:

 @transform name begin
  label = action
 end

 For example, a simple graph grammar might look like:

 @grammar nodetest begin
   start = +node_def
   node_def = node_label + node_name + lbrace + data + rbrace
   node_name = string_value + space

   data = *(line + semicolon)
   line = string_value + space
   string_value = r[_a-zA-Z][_a-zA-Z0-9]*

   lbrace = { + space
   rbrace = } + space
   semicolon = ; + space
   node_label = node + space
   space = r[ \t\n]*
 end

 with it's actions to create some data structure:

 type MyNode
   name
   values

   function MyNode(name, values)
 new(name, values)
   end
 end


 with:
 @transform tograph begin
   # ignore these
   lbrace = nothing
   rbrase = nothing
   semicolon = nothing
   node_label = nothing
   space = nothing

   # special action so we don't have to define every label
   default = children

   string_value = node.value
   value = node.value
   line = children
   data = MyNode(, children)
   node_def = begin
 local name = children[1]
 local cnode = children[2]
 cnode.name = name
 return cnode
   end
 end

 and finally, to apply the transform:

 (ast, pos, error) = parse(nodetest, data)
 result = apply(tograph, ast)
 println(result)# {MyNode(foo,{a,b}),MyNode(bar,{c,d})}

 The magic in '@transform' basically just creates the dictionary like 
 before, but automatically wraps the expression on the RHS  as an anonymous 
 function  (node, children) - expr.

 I'm currently looking for a better name than 'children', as it's 
 potentially confusing and misleading. It's actually the values of the child 
 nodes (as opposed to node.children). Maybe cvalues?

 On Sunday, May 25, 2014 10:28:45 PM UTC-4, Abe Schneider wrote:

 I wrote a quick PEG Parser for Julia with Packrat capabilities:

 https://github.com/abeschneider/PEGParser

 It's a first draft and needs a ton of work, testing, etc., but if this is 
 of interest to anyone else, here is a quick description.

 Grammars can be defined using most of the standard EBNF syntax. For 
 example, a simple math grammar can be defined as:

 @grammar mathgrammar begin

   start = expr
   number = r([0-9]+)
   expr = (term + op1 + expr) | term
   term = (factor + op2 + term) | factor
   factor = number | pfactor
   pfactor = ('(' + expr + ')')
   op1 = '+' | '-'
   op2 = '*' | '/'
 end



 To parse a string with the grammar:

 (node, pos, error) = parse(mathgrammar, 5*(2-6))

 This will create an AST which can then be transformed to a value. 
 Currently this is accomplished by doing:

 math = Dict()

 math[number] = (node, children) - float(node.value)
 math[expr] = (node, children) -
 length(children) == 1 ? children : eval(Expr(:call, children[2], 
 children[1], children[3]))
 math[factor] = (node, children) - children
 math[pfactor] = (node, children) - children[2]
 math[term] = (node, children) -
 length(children) == 1 ? children : eval(Expr(:call, children[2], 
 children[1], children[3]))
 math[op1] = (node, children) - symbol(node.value)
 math[op2] = (node, children) - symbol(node.value)


 Ideally, I would like to simplify this to using multi-dispatch on symbols 
 (see previous post), but for now this is the easiest way to define actions 
 based on node attributes.

 Finally, to transform the tree:

 result = transform(math, node)  # will give the value of 20

 Originally I was going to attach the transforms to the rules themselves 
 (similiar to boost::spirit). However, there were two reasons for not doing 
 this:

1. To implement the packrat part of the parser, I needed to cache the 
results which meant building an AST anyways
2. It's nice to be apply to get different transforms for the same 
grammar (e.g. you may want to transform the result into HTML, LaTeX, etc.)

 The downside of the separation is that it adds some more complexity to 
 the process.



[julia-users] Re: Strange macro behavior?

2014-06-04 Thread Abe Schneider
Here's a simple example of what I'm observing:

testmodule.jl
module testmodule

export @wrapexpr

# if I put foo here, everything works
# foo(x, y) = x*y

macro wrapexpr(expr)
  quote
(x, y) - $(expr)
  end
end

end

and testscript.jl:
using testmodule

foo(x, y) = x*y

fn1 = @wrapexpr x+y
fn2 = @wrapexpr begin foo(x, y) end

println(fn1 = , fn1(1, 2))
println(fn2 = , fn2(1, 2))

with the output:
fn1 = 3
ERROR: foo not defined
 in anonymous at /home/abraham/tmp/testmodule.jl:6
 in include at boot.jl:244
 in include_from_node1 at loading.jl:128
while loading /home/abraham/tmp/testscript.jl, in expression starting on 
line 9

but if I define foo in the module (the commented out line), I get:
fn1 = 3
fn2 = 2




On Tuesday, June 3, 2014 9:59:25 PM UTC-4, Abe Schneider wrote:

 I have a macro that is defined in a module that creates a dictionary of 
 anonymous functions. These anonymous functions wrap arbitrary code which I 
 pass in. If I  pass in simple pieces of code (e.g. just returning a simple 
 value), my test script everything works as expected.

 However, if I make a function in my test script, which then gets wrapped 
 in an anonymous function (e.g. I do a begin/end block), I get an error that 
 the function is not defined. But, if I move the function out of my test 
 script to my module, everything works.

 I assume what is happening is that when the anonymous function is being 
 made, it sees only the namespace of the module. This almost makes sense to 
 me, except that the macro is being called from my test script, so the 
 namespace should also be in the script.

 Is this expected behavior? If so, are there any suggestions on how to get 
 around this?

 I can provide code if it will be helpful (I thought in this case it might 
 just make things more complicated). Also, I'm using Julia version 
 0.3.0-prerelease+3337.

 Thanks!



[julia-users] Re: Strange macro behavior?

2014-06-04 Thread Abe Schneider
I should add, I suspect that 'esc' can only be used in a quote block, so I 
tried this instead:

macro wrapexpr(expr)
  quote
($(esc(x)), $(esc(y))) - $(esc(expr))
  end
end

But get:

ERROR: x not defined



On Wednesday, June 4, 2014 11:44:43 AM UTC-4, David Moon wrote:

 I have a pending pull request #6910 to fix macros to behave as you expect, 
 but until that gets integrated you will need to use the esc function in 
 your macro to tell the macro system that x, y, and expr are in the macro 
 caller's context, not the macro definition's context.  There is no 
 guarantee that my changes will ever be integrated, but with those changes 
 you would write:

 macro wrapexpr(expr)
   quote
 ($:x, $:y) - $(expr)
   end
 end

 Without my changes I think you would write:

 macro wrapexpr(expr)
   x = esc(:x)
   y = esc(:y)
   quote
 ($x, $y) - $(esc(expr))
   end
 end

 but I have not tested it.



[julia-users] Re: Strange macro behavior?

2014-06-04 Thread Abe Schneider
I got it to work with:

macro wrapexpr(expr)
  x = :x
  y = :y
  quote
$(esc(quote ($x, $y) - $expr end))
  end
end

I think the problem before was that the entire anonymous function has to be 
escaped. I also don't claim to understand hygiene well enough to really 
understand what that means.

Hopefully your pull goes through!


On Wednesday, June 4, 2014 11:44:43 AM UTC-4, David Moon wrote:

 I have a pending pull request #6910 to fix macros to behave as you expect, 
 but until that gets integrated you will need to use the esc function in 
 your macro to tell the macro system that x, y, and expr are in the macro 
 caller's context, not the macro definition's context.  There is no 
 guarantee that my changes will ever be integrated, but with those changes 
 you would write:

 macro wrapexpr(expr)
   quote
 ($:x, $:y) - $(expr)
   end
 end

 Without my changes I think you would write:

 macro wrapexpr(expr)
   x = esc(:x)
   y = esc(:y)
   quote
 ($x, $y) - $(esc(expr))
   end
 end

 but I have not tested it.



Re: [julia-users] Re: PEG Parser

2014-06-04 Thread Abe Schneider
I'll try to get around to comparing against the DataFrames version and 
profiling this week. I got stuck trying to figure out the action semantics.

On Tuesday, May 27, 2014 6:58:42 PM UTC-4, John Myles White wrote:

 I'd be really interested to see how this parser compares with DataFrames. 
 There's a bunch of test files in the DataFrames.jl/test directory.

  -- John

 On May 27, 2014, at 3:49 PM, Abe Schneider abe.sc...@gmail.com 
 javascript: wrote:

 I don't know how the speed of the parser will be compared to DataFrames -- 
 I've done absolutely no work to date on profiling the code, but I thought 
 writing a CSV parser was a good way to test out code (and helped find a 
 bunch of bugs).

 I've also committed (under examples/) the CSV parser. The grammar (from 
 the RFC) is:

 @grammar csv begin
   start = data
   data = record + *(crlf + record)
   record = field + *(comma + field)
   field = escaped_field | unescaped_field
   escaped_field = dquote + *(textdata | comma | cr | lf | dqoute2) + 
 dquote
   unescaped_field = textdata
   textdata = r[ !#$%'()*+\-./0-~]+
   cr = '\r'
   lf = '\n'
   crlf = cr + lf
   dquote = ''
   dqoute2 = \\
   comma = ','
 end

 and the actions are:

 tr[crlf] = (node, children) - nothing
 tr[comma] = (node, children) - nothing

 tr[escaped_field] = (node, children) - node.children[2].value
 tr[unescaped_field] = (node, children) - node.children[1].value
 tr[field] = (node, children) - children
 tr[record] = (node, children) - unroll(children)
 tr[data] = (node, children) - unroll(children)
 tr[textdata] = (node, children) - node.value


 give the data:

 parse_data = 1,2,3\r\nthis is,a test,of csv\r\nthese,are,quotes (
 )

 and running the parser:

 (node, pos, error) = parse(csv, parse_data)
 result = transform(tr, node)

 I get:

 {{1,2,3},{this is,a test,of csv},{these,are,quotes 
 (\\)}}





 On Monday, May 26, 2014 3:41:26 AM UTC-4, harven wrote:

 Nice!

 If you are interested by testing your library on a concrete problem, you 
 may want to parse comma separated value (csv) files. The bnf is in the 
 specification RFC4180. http://tools.ietf.org/html/rfc4180

 AFAIK, the readcsv function provided in Base does not handle quotations 
 well whereas the csv parser in DataFrames is slow, so that julia does not 
 have yet a native efficient way to parse csv files.




Re: [julia-users] parsers?

2014-06-03 Thread Abe Schneider
Currently it only handles strings. The reason is that PEG theoretically 
have infinite look-ahead. I think this can be made a little better by 
having a stream that loads data on-demand. In general, I think PEG's choice 
of memory over speed is good for many things, but you'll probably find some 
data where an infinite look-ahead isn't a good idea.

I have a very simple error handling in place (I based it on how Parsimonous 
works), but it definitely needs a lot of work. One big question I'm trying 
to figure out is whether it's better to return an error as a value or raise 
an exception. I've gone with returning a value so (at a later date) the 
errors can be collected. Also, errors are currently only emitted for 
non-matches, but it should be possible for the transforms to also emit 
errors.

I think everything but the rules are typed. The only reason the rules 
aren't typed was that when I originally wrote the code I wasn't sure their 
exact value at the time. I originally wrote EBNF for an entirely different 
reason and got side-tracked when I realized I could write a parser with it.

A

On Monday, June 2, 2014 6:41:18 PM UTC-4, andrew cooke wrote:


 random, possibly clueless thoughts as i look at this:

 yes, transform rules by type would be nice!  not sure what that means 
 about having to generate a module within a macro, though (for namespacing).

 do you parse strings or streams?  (or both?)  i know nothing about julia 
 streams, yet, but i imagine streams would make it easier to abstract away 
 nasty book-keeping for error reporting (line number etc).

 do you have any support for error handling?

 why aren't any of your type contents typed?  can julia infer that from 
 use?  if not, it will have a big impact on speed and memory use, i would 
 guess.  even better if they can be immutable.

 thanks,
 andrew

 On Saturday, 31 May 2014 21:10:37 UTC-4, Abe Schneider wrote:

 I should add that PEGParser's code is fairly new and untested (besides 
 having an  uninspired name). I'm also hoping to have better action 
 semantics soon.

 On Saturday, May 31, 2014 2:17:27 PM UTC-4, andrew cooke wrote:

 https://groups.google.com/d/msg/julia-users/t56VxOX1vvk/nszQYWP_pm4J

 https://groups.google.com/d/msg/julia-users/6jz3Ow5SAAE/TgKHQ48gUG4J

 thanks!

 On Saturday, 31 May 2014 14:04:28 UTC-4, Isaiah wrote:

 There was a nice looking PEG system previewed a few days ago if you 
 search the users list (and I think there was another one several months 
 back by Michael Fox).


 On Sat, May 31, 2014 at 1:22 PM, andrew cooke and...@acooke.org 
 wrote:

 are there any libraries for parsing in julia?  either parser 
 combinator or something more traditional (maybe a wrapper for something 
 like antlr)?

 all i can find is an old discussion started by leah h in which jeff b 
 suggests doing everything in julia.  that included a pointer to 
 https://github.com/astrieanna/juliaparsec/blob/master/juliaparsec.jl 
 from dan l which is, well, as he says, rather basic.

 i'm not sure i agree, but i don't want to write my own combinator lib 
 either.

 i guess i'm looking for things like a clean separation between grammar 
 and implementation, support for errors with line numbers, speed, easy 
 debugging...

 andrew




Re: [julia-users] parsers?

2014-06-03 Thread Abe Schneider
Yeah, that's a good point. I think instead of using a string an iterator 
should be used. It should be fairly easy to replace the 
string-implementation with an iterator-implementation.

On Tuesday, June 3, 2014 9:27:05 PM UTC-4, andrew cooke wrote:



 On Tuesday, 3 June 2014 08:29:31 UTC-4, andrew cooke wrote:



 On Tuesday, 3 June 2014 08:16:49 UTC-4, Abe Schneider wrote:

 Currently it only handles strings. The reason is that PEG theoretically 
 have infinite look-ahead. I think this can be made a little better by 
 having a stream that loads data on-demand. In general, I think PEG's choice 
 of memory over speed is good for many things, but you'll probably find some 
 data where an infinite look-ahead isn't a good idea.


 yeah, i'm sitting here now thinking about this.  i just realised that 
 what i have used in the past (i wrote lepl which was an alternative to 
 pyparsing) is effectively an immutable stream.  reading from one returns a 
 tuple of (char, newstream) so you can cache the streams and re-use them on 
 backtracking.  but that doesn't fit well with julia's IOStream abstraction 
 (from first glance at least).  so i am stuck and came here to waste time 
 reading newsgroup posts..


 duh.  this is equivalent to a julia iterator.

 I have a very simple error handling in place (I based it on how 
 Parsimonous works), but it definitely needs a lot of work. One big question 
 I'm trying to figure out is whether it's better to return an error as a 
 value or raise an exception. I've gone with returning a value so (at a 
 later date) the errors can be collected. Also, errors are currently only 
 emitted for non-matches, but it should be possible for the transforms to 
 also emit errors.


 ok, i will look at parsimonous, thanks.  i never thought much about 
 multiple errors.
  

 I think everything but the rules are typed. The only reason the rules 
 aren't typed was that when I originally wrote the code I wasn't sure their 
 exact value at the time. I originally wrote EBNF for an entirely different 
 reason and got side-tracked when I realized I could write a parser with it.

 A

 On Monday, June 2, 2014 6:41:18 PM UTC-4, andrew cooke wrote:


 random, possibly clueless thoughts as i look at this:

 yes, transform rules by type would be nice!  not sure what that means 
 about having to generate a module within a macro, though (for namespacing).

 do you parse strings or streams?  (or both?)  i know nothing about 
 julia streams, yet, but i imagine streams would make it easier to abstract 
 away nasty book-keeping for error reporting (line number etc).

 do you have any support for error handling?

 why aren't any of your type contents typed?  can julia infer that from 
 use?  if not, it will have a big impact on speed and memory use, i would 
 guess.  even better if they can be immutable.

 thanks,
 andrew

 On Saturday, 31 May 2014 21:10:37 UTC-4, Abe Schneider wrote:

 I should add that PEGParser's code is fairly new and untested (besides 
 having an  uninspired name). I'm also hoping to have better action 
 semantics soon.

 On Saturday, May 31, 2014 2:17:27 PM UTC-4, andrew cooke wrote:

 https://groups.google.com/d/msg/julia-users/t56VxOX1vvk/nszQYWP_pm4J

 https://groups.google.com/d/msg/julia-users/6jz3Ow5SAAE/TgKHQ48gUG4J

 thanks!

 On Saturday, 31 May 2014 14:04:28 UTC-4, Isaiah wrote:

 There was a nice looking PEG system previewed a few days ago if you 
 search the users list (and I think there was another one several months 
 back by Michael Fox).


 On Sat, May 31, 2014 at 1:22 PM, andrew cooke and...@acooke.org 
 wrote:

 are there any libraries for parsing in julia?  either parser 
 combinator or something more traditional (maybe a wrapper for 
 something 
 like antlr)?

 all i can find is an old discussion started by leah h in which jeff 
 b suggests doing everything in julia.  that included a pointer to 
 https://github.com/astrieanna/juliaparsec/blob/master/juliaparsec.jl 
 from dan l which is, well, as he says, rather basic.

 i'm not sure i agree, but i don't want to write my own combinator 
 lib either.

 i guess i'm looking for things like a clean separation between 
 grammar and implementation, support for errors with line numbers, 
 speed, 
 easy debugging...

 andrew




[julia-users] Strange macro behavior?

2014-06-03 Thread Abe Schneider
I have a macro that is defined in a module that creates a dictionary of 
anonymous functions. These anonymous functions wrap arbitrary code which I 
pass in. If I  pass in simple pieces of code (e.g. just returning a simple 
value), my test script everything works as expected.

However, if I make a function in my test script, which then gets wrapped in 
an anonymous function (e.g. I do a begin/end block), I get an error that 
the function is not defined. But, if I move the function out of my test 
script to my module, everything works.

I assume what is happening is that when the anonymous function is being 
made, it sees only the namespace of the module. This almost makes sense to 
me, except that the macro is being called from my test script, so the 
namespace should also be in the script.

Is this expected behavior? If so, are there any suggestions on how to get 
around this?

I can provide code if it will be helpful (I thought in this case it might 
just make things more complicated). Also, I'm using Julia version 
0.3.0-prerelease+3337.

Thanks!


Re: [julia-users] parsers?

2014-05-31 Thread Abe Schneider
I should add that PEGParser's code is fairly new and untested (besides 
having an  uninspired name). I'm also hoping to have better action 
semantics soon.

On Saturday, May 31, 2014 2:17:27 PM UTC-4, andrew cooke wrote:

 https://groups.google.com/d/msg/julia-users/t56VxOX1vvk/nszQYWP_pm4J

 https://groups.google.com/d/msg/julia-users/6jz3Ow5SAAE/TgKHQ48gUG4J

 thanks!

 On Saturday, 31 May 2014 14:04:28 UTC-4, Isaiah wrote:

 There was a nice looking PEG system previewed a few days ago if you 
 search the users list (and I think there was another one several months 
 back by Michael Fox).


 On Sat, May 31, 2014 at 1:22 PM, andrew cooke and...@acooke.org wrote:

 are there any libraries for parsing in julia?  either parser combinator 
 or something more traditional (maybe a wrapper for something like antlr)?

 all i can find is an old discussion started by leah h in which jeff b 
 suggests doing everything in julia.  that included a pointer to 
 https://github.com/astrieanna/juliaparsec/blob/master/juliaparsec.jl 
 from dan l which is, well, as he says, rather basic.

 i'm not sure i agree, but i don't want to write my own combinator lib 
 either.

 i guess i'm looking for things like a clean separation between grammar 
 and implementation, support for errors with line numbers, speed, easy 
 debugging...

 andrew




[julia-users] Re: PEG Parser

2014-05-27 Thread Abe Schneider
I don't know how the speed of the parser will be compared to DataFrames -- 
I've done absolutely no work to date on profiling the code, but I thought 
writing a CSV parser was a good way to test out code (and helped find a 
bunch of bugs).

I've also committed (under examples/) the CSV parser. The grammar (from the 
RFC) is:

@grammar csv begin
  start = data
  data = record + *(crlf + record)
  record = field + *(comma + field)
  field = escaped_field | unescaped_field
  escaped_field = dquote + *(textdata | comma | cr | lf | dqoute2) + dquote
  unescaped_field = textdata
  textdata = r[ !#$%'()*+\-./0-~]+
  cr = '\r'
  lf = '\n'
  crlf = cr + lf
  dquote = ''
  dqoute2 = \\
  comma = ','
end

and the actions are:

tr[crlf] = (node, children) - nothing
tr[comma] = (node, children) - nothing

tr[escaped_field] = (node, children) - node.children[2].value
tr[unescaped_field] = (node, children) - node.children[1].value
tr[field] = (node, children) - children
tr[record] = (node, children) - unroll(children)
tr[data] = (node, children) - unroll(children)
tr[textdata] = (node, children) - node.value


give the data:

parse_data = 1,2,3\r\nthis is,a test,of csv\r\nthese,are,quotes ()


and running the parser:

(node, pos, error) = parse(csv, parse_data)
result = transform(tr, node)

I get:

{{1,2,3},{this is,a test,of csv},{these,are,quotes (\\)
}}





On Monday, May 26, 2014 3:41:26 AM UTC-4, harven wrote:

 Nice!

 If you are interested by testing your library on a concrete problem, you 
 may want to parse comma separated value (csv) files. The bnf is in the 
 specification RFC4180. http://tools.ietf.org/html/rfc4180

 AFAIK, the readcsv function provided in Base does not handle quotations 
 well whereas the csv parser in DataFrames is slow, so that julia does not 
 have yet a native efficient way to parse csv files.



[julia-users] Re: PEG Parser

2014-05-27 Thread Abe Schneider
I'll take a look. I found the full grammar here:

http://www.graphviz.org/doc/info/lang.html

Unfortunately I have very little free time (most of the work was done 
during vacation), but it shouldn't be too difficult to implement.

On Monday, May 26, 2014 4:35:52 PM UTC-4, Miles Gould wrote:

 Nice indeed! We'd also welcome a parser for the dot format in Graphs.jl :-)

 https://en.wikipedia.org/wiki/DOT_%28graph_description_language%29

 Miles

 On Monday, 26 May 2014 08:41:26 UTC+1, harven wrote:

 Nice!

 If you are interested by testing your library on a concrete problem, you 
 may want to parse comma separated value (csv) files. The bnf is in the 
 specification RFC4180. http://tools.ietf.org/html/rfc4180

 AFAIK, the readcsv function provided in Base does not handle quotations 
 well whereas the csv parser in DataFrames is slow, so that julia does not 
 have yet a native efficient way to parse csv files.



[julia-users] PEG Parser

2014-05-25 Thread Abe Schneider
I wrote a quick PEG Parser for Julia with Packrat capabilities:

https://github.com/abeschneider/PEGParser

It's a first draft and needs a ton of work, testing, etc., but if this is 
of interest to anyone else, here is a quick description.

Grammars can be defined using most of the standard EBNF syntax. For 
example, a simple math grammar can be defined as:

@grammar mathgrammar begin

  start = expr
  number = r([0-9]+)
  expr = (term + op1 + expr) | term
  term = (factor + op2 + term) | factor
  factor = number | pfactor
  pfactor = ('(' + expr + ')')
  op1 = '+' | '-'
  op2 = '*' | '/'
end



To parse a string with the grammar:

(node, pos, error) = parse(mathgrammar, 5*(2-6))

This will create an AST which can then be transformed to a value. Currently 
this is accomplished by doing:

math = Dict()

math[number] = (node, children) - float(node.value)
math[expr] = (node, children) -
length(children) == 1 ? children : eval(Expr(:call, children[2], 
children[1], children[3]))
math[factor] = (node, children) - children
math[pfactor] = (node, children) - children[2]
math[term] = (node, children) -
length(children) == 1 ? children : eval(Expr(:call, children[2], 
children[1], children[3]))
math[op1] = (node, children) - symbol(node.value)
math[op2] = (node, children) - symbol(node.value)


Ideally, I would like to simplify this to using multi-dispatch on symbols 
(see previous post), but for now this is the easiest way to define actions 
based on node attributes.

Finally, to transform the tree:

result = transform(math, node)  # will give the value of 20

Originally I was going to attach the transforms to the rules themselves 
(similiar to boost::spirit). However, there were two reasons for not doing 
this:

   1. To implement the packrat part of the parser, I needed to cache the 
   results which meant building an AST anyways
   2. It's nice to be apply to get different transforms for the same 
   grammar (e.g. you may want to transform the result into HTML, LaTeX, etc.)

The downside of the separation is that it adds some more complexity to the 
process.


[julia-users] Design question

2014-05-24 Thread Abe Schneider
I'm currently working on a problem where I have a tree structure composed 
of:

type Node
  value
  label
  children
end

which I want to traverse and have different functions called depending on 
the value of label. Normally I would just sub-type Node. However, the 
results are coming from a parser which allows the user to specify a myriad 
of different types. Thus, 'label' depends on the particular parse rule 
executed.

The traversal code would look something like:

function transform(fn, node)
  cvalues = [transform(fn, child) for child in node.children] 
  return fn(node, cvalues, node.label)
end

The question is the how to get Julia to select the correct function to call 
based on 'node.label'. For example, I might have something like:

htmlformat(node, children, label_is_x) = tag
htmlformat(node, children, label_is_y) = /tag

Two methods I've come up with so far to do this are:

   1. Use the PatternDispatch package
   2. Automatically create types that can be used as labels for selecting 
   the proper function


I'm currently exploring the first choice (why re-invent the wheel?). 
However, it seems like it might still be a more direct approach to generate 
types as labels. For example, I could generate the types when generating 
the grammars:


macro maketype(label)
  quote
type $(esc(label)) end 
  end
end

which then could be used directly in the methods. Has anyone else tried 
this approach before? Are there known potential issues? It seems like this 
could be a nice general approach for a light-weight version of the 
PatternDispatch.


Thanks!


[julia-users] Re: logical indexing... broadcasting

2014-05-16 Thread Abe Schneider
I might try something like (note the code code is written for clarity, not 
for compactness or completeness):

function encode_name(name::String)
  if name == setosa
return [1 0 2];
  elseif name == versicolor
 return [2 1 0];
  else
return [0 2 1];
  end
end

output = map(encode_name, iris_data)



On Wednesday, May 14, 2014 8:05:50 AM UTC-4, Héctor Fabio Satizábal Mejía 
wrote:

 Hello

 I am trying to conduct some tests on machine learning algorithms with 
 Julia but given that I am new to the language I am kind of stuck in a very 
 simple thing.

 I am working with the Iris dataset, and I want to translate the species 
 name into a code like this:

 setosa = [1 0 2]
 versicolor = [2 1 0]
 virginica = [0 2 1]

 I would like to have something like:

 using RDatasets
 iris_data = dataset(datasets, iris);

 iris_output = zeros(length(iris_data.columns[5]), 3);
 iris_output[iris_data.columns[5].==setosa,:] = [1 0 2];
 iris_output[iris_data.columns[5].==versicolor,:] = [2 1 0];
 iris_output[iris_data.columns[5].==virginica,:] = [0 2 1];

 Unfortunately this is not working. I get this error message:

 ERROR: DimensionMismatch(tried to assign 1x3 array to 50x3 destination)

 Which I think is a broadcasting problem.

 Any help? Is there a compact way of doing that?

 Thanks in advance

 Héctor


 By the way, I manage to do this in R using the following code:

 iris.data - iris
 iris.output - matrix(0, 3, 150)
 iris.output[,iris.data[,5]==setosa] - c(1,0,0)
 iris.output[,iris.data[,5]==versicolor] - c(0,1,0)
 iris.output[,iris.data[,5]==virginica] - c(0,0,1)
 iris.output - t(iris.output)





[julia-users] Re: Macro question

2014-05-15 Thread Abe Schneider
You are correct -- it's weird, because I'm sure I tested it several times 
before posting, but I now get '5', as you suggest.

On Thursday, May 15, 2014 7:51:15 AM UTC-4, Mike Innes wrote:

 I think your second snippet must have gotten a bit muddled, since `expr` 
 should end up with the value 5.

 macro createVar(name, value)
   quote
 $name = $value;
   end
 end

 expr = @createVar foo 5
 # This is equivalent to `expr = (foo = 5)`, *not* `expr = :(foo = 5)`

 expr == 5

 If you do want `createVar` to return an expression, it should be a 
 function instead of a macro. Maybe try running the example again to check 
 it's behaving in the expected way?


 On Thursday, 15 May 2014 12:29:13 UTC+1, Abe Schneider wrote:

 As an experiment I wrote a simple macro to set a variable:

 macro createVar(name, value)
   eval(quote
 $name = $value;
   end)
 end

 which works as expected:

 @createVar foobar 5;
 println(foobar = $foobar); # foobar = 5 (OK)

 However, if I instead do:

 macro createVar(name, value)
   quote
 $name = $value;
   end
 end

 expr = @createVar(foobar, 5);

 println($expr); # foobar = 5 (OK)

 # now evaluate the expression to do the actual assignment
 eval(expr);
 println(foobar = $foobar);

 I get ERROR: foobar not defined. I would expect that if I do the eval 
 outside of the macro I should get the same result as doing the eval inside 
 the macro. Is this expected behavior?

 I should add that I'm using a version of 0.3 from the repository.



[julia-users] Re: Macro question

2014-05-15 Thread Abe Schneider
That works, thanks! 


On Thursday, May 15, 2014 8:00:29 AM UTC-4, Mike Innes wrote:

 Oh, the other thing I should point out (sorry to post repeatedly) is that 
 the macro hygiene pass will mean that `foo` is not actually defined by this 
 macro. You probably want:

 macro createVar(name, value)
   quote
 $(esc(name)) = $value;
   end
 end

 See the 
 hygienehttp://docs.julialang.org/en/latest/manual/metaprogramming/#hygienesection
  of the manual.

 On Thursday, 15 May 2014 12:53:13 UTC+1, Mike Innes wrote:

 Alternatively

 macroexpand(:@createVar(foo, 5))

 Might have the desired behaviour.


 On Thursday, 15 May 2014 12:51:15 UTC+1, Mike Innes wrote:

 I think your second snippet must have gotten a bit muddled, since `expr` 
 should end up with the value 5.

 macro createVar(name, value)
   quote
 $name = $value;
   end
 end

 expr = @createVar foo 5
 # This is equivalent to `expr = (foo = 5)`, *not* `expr = :(foo = 5)`

 expr == 5

 If you do want `createVar` to return an expression, it should be a 
 function instead of a macro. Maybe try running the example again to check 
 it's behaving in the expected way?


 On Thursday, 15 May 2014 12:29:13 UTC+1, Abe Schneider wrote:

 As an experiment I wrote a simple macro to set a variable:

 macro createVar(name, value)
   eval(quote
 $name = $value;
   end)
 end

 which works as expected:

 @createVar foobar 5;
 println(foobar = $foobar); # foobar = 5 (OK)

 However, if I instead do:

 macro createVar(name, value)
   quote
 $name = $value;
   end
 end

 expr = @createVar(foobar, 5);

 println($expr); # foobar = 5 (OK)

 # now evaluate the expression to do the actual assignment
 eval(expr);
 println(foobar = $foobar);

 I get ERROR: foobar not defined. I would expect that if I do the eval 
 outside of the macro I should get the same result as doing the eval inside 
 the macro. Is this expected behavior?

 I should add that I'm using a version of 0.3 from the repository.



[julia-users] Re: tree style

2014-05-14 Thread Abe Schneider
Just in terms of implementing trees, I would do something like:

abstract Node;

type Leaf : Node
value::Float64;
end

type Branch : Node
left::Node;
right::Node;
end
  


This should allow you to write methods that target either branch or leafs 
accordingly:

function sum(node::Branch)
value::Float64 = 0;
value += !isEmpty(node.left) ? sum(node.left) : 0;
value += !isEmpty(node.right) ? sum(node.right) : 0;
end

function sum(node::Leaf)
return node.value;
end




On Tuesday, May 13, 2014 11:47:14 PM UTC-4, Abram Demski wrote:

 Hi all,

 I'm implementing BSP trees, and I've run into a style issue which I'm 
 uncertain about.

 For my current purposes, the trees will be holding floats, but I wanted to 
 write things in a way which allowed other possibilities later. At first, I 
 made an explicit Leaf type:

 *Version 1*


 abstract Leaf


 type FloatLeaf : Leaf

 value::Float64

 end


 abstract Split # abstract type for space partition


 # starting out with axis-aligned splits, to implement arbitrary-angle later.

 # Axis-aligned splits make rectangles, hence RectSplit

 type RectSplit : Split

 var::Int

 loc::Float64

 end


 # internal tree node. Two sides of a split are pos and neg.

 type TreeNode

 split::Split # split definition

 pos::Union(TreeNode, Leaf)  # negative side

 neg::Union(TreeNode, Leaf)  # positive side

 end


 (This is actually a bit simplified; I also had a special Nothing type to 
 indicate an empty case. The NA type from dataframes was not appropriate 
 because I wanted different behavior.)

 I implemented functions on the trees mainly by using multi-dispatch in a 
 pattern-matching style, matching against TreeNode or Leaf types to 
 differentiate between the recursive case and the base case.

 I eventually decided that the Leaf type seemed rather pointless, because 
 it was just a container for a value. Using a Leaf type created some 
 annoyance with defining functions to operate on leaves, when the obvious 
 thing to do was just apply those functions to the leaf values. Also, I was 
 a little worried that putting stuff inside a Leaf container would be a 
 small efficiency hit (probably not much?).

 End result, I modified to this:

 *Version 2*

 abstract Split


 type RectSplit : Split

 var::Int

 loc::Float64

 end


 type TreeNode{a}

 split::Split # split definition

 pos::Union(TreeNode{a}, a)  # negative side

 neg::Union(TreeNode{a}, a)  # positive side

 end


 This is shorter, which seems like a good sign. It also manages to indicate 
 that all leafs should have the same type, which the previous version 
 didn't. However, I couldn't keep using multiple dispatch to define the 
 different cases for my functions. The closest thing I could do would be to 
 make the cases which match to Leaf type match to Float instead. This works 
 when the tree is only holding floats, but I wanted to handle more general 
 cases.

 Since this didn't seem right, I switched most of my code to use if-else in 
 one function rather than multiple dispatch on the types. Leaving the leaf 
 case for the final else allows me to write things in a generic way (no 
 explicit assumption that I'm dealing with Floats in functions that don't 
 need to interact with this assumption).

 However, this approach still doesn't work if I want to write a method 
 which applies to trees (be they internal nodes or leaf nodes) but allows 
 other function definitions for other types. Anything which isn't a TreeNode 
 is now assumed to be a leaf, the way I've done it. This isn't actually a 
 problem yet, but it could be at some point.

 Does this mean I was wrong to switch to the 2nd version?

 Any other suggestions for how this should go?

 Best,

 Abram