On Wednesday, February 26, 2014, Ivar Nesje <iva...@gmail.com> wrote:

> How is getters/setters -> MethodError(b, (a,)) better than direct field
> access -> ErrorException("type a has no field b")?
>
> They seem equivalent to me.
>

I guess calling them getters and setters might be misleading, but generally
it's a good idea to minimize coupling. Using direct field access deeply
couples the function to the implementation. The function interface reduces
that somewhat.

I may, e.g., want to know the width of a GraphicsDevice. In one
implementation, say PDF output, that might just be a field of a concrete
type. In another, say for a screen, it might be C function call. The
function interface lets us handle both.

 Kevin


> kl. 17:47:32 UTC+1 onsdag 26. februar 2014 skrev Kevin Squire følgende:
>>
>> Hello Robert,
>>
>> Thanks for posting this question.  This is something I've struggled with
>> and attempted to address in a couple of different ways.  I'm not totally
>> happy with either of the solutions, but I'll share them in the hope that
>> they're useful.
>>
>> 1. One method you did not mention was to implement everything against an
>> abstract base class, but override individual functions for different
>> concrete classes.  To avoid depending on the actual type implementation,
>> additional functions are defined on the concrete types which give access to
>> the data.
>>
>> A couple of variations on this include the GraphicsDevice interface in
>> Julia (https://github.com/JuliaLang/julia/blob/master/base/
>> graphics.jl#L177-L192), and Graphs.jl (http://julialang.org/Graphs.
>> jl/interface.html#interface-declaration-and-verification).
>>
>> This is a pretty good solution, although how well it works is problem
>> dependent.  I've sometimes found it challenging/annoying to design
>> "getters" and "setters" just to make sure that the functions and types are
>> only loosely coupled.
>>
>> 2. I used your third design pattern when implementing OrderedDicts (
>> https://github.com/JuliaLang/DataStructures.jl/blob/master/
>> src/ordereddict.jl), and used John Miles White's @delegate macro to
>> simplify the code (https://github.com/JuliaLang/
>> DataStructures.jl/blob/master/src/delegate.jl).
>>
>> The @delegate macro makes the code less cluttered, but has the downside
>> in that you don't have access to other/new methods for the wrapped type
>> unless you specify them.
>>
>> Hope this is useful.  Cheers!
>>
>>   Kevin
>>
>>
>> On Tue, Feb 25, 2014 at 10:44 PM, Robert Feldt <robert...@gmail.com>wrote:
>>
>>> I really like Julia's dispatch mechanisms, type system and so on. I have
>>> found a number of different ways I use it to design libraries and programs.
>>> But it would be great with some patterns/ideas/feedback from more seasoned
>>> Julia programmers. What are your Julia Design Patterns?
>>>
>>> A concrete situation that I have struggled somewhat with is how to best
>>> design in Julia for the situation where I have one main/default
>>> algorithms/set-of-behaviors+data but then with a multitude of small
>>> variations. Typically there is a large set of data and methods/functions
>>> that are the same for the whole class of things and there are only 1-4
>>> functions/methods that need to change for each variation. An example from
>>> BlackBoxOptim ( https://github.com/robertfeldt/BlackBoxOptim.jl ) is
>>> where there is one type for DifferentialEvolution and then multiple
>>> different variants of DE where only 1-2 functions differ from the "base" DE
>>> one.
>>>
>>> I have found a few different "design patterns" for this situation but
>>> not sure what is the long-term best:
>>>
>>> 1. Have a few Function fields in the "base" (composite) type which are
>>> set up at construction time and that implements the variant-specific
>>> behaviors. This is simple and direct but feels a bit "un-Julia" since it
>>> does not really use the dispatch system. One also has to predict the
>>> variation points (here: function) upfront which might not be flexible
>>> enough. Also performance might suffer since the types of the function not
>>> known.
>>>
>>> 2. Have one XBase type which includes a field of an abstract XStrategy
>>> type where specific sub-types to XStrategy implements each variant by
>>> implementing variant-specific functionality. This seems fairly efficient,
>>> but again one has to predict more or less where the variations should
>>> happen since the functions on the XBase type need to call to the XStrategy
>>> functions.
>>>
>>> 3. Have one XBase type which is then included as a field in specific
>>> variants. This seems efficient and flexible but the code is somewhat
>>> cluttered in that one has to have one extra indirection when accessing
>>> common data/fields (this is a similar problem in 2 above though).
>>>
>>> 4. "Copy" the common data/fields of XBase into each specific variant.
>>> This is the most flexible and should have high performance but there seem
>>> to be a risk that bugs have to be changed in multile source code locations
>>> since it is a kind of "copy-paste reuse".
>>>
>>> Would be great to hear your advice/feedback on how you design in/with
>>> the Julia type and dispatch system.
>>>
>>> Thanks,
>>>
>>> Robert Feldt
>>>
>>
>>

Reply via email to