# Overriding methods with closures?

Hi,

Is it possible to override a method with a closure?

``````function add(x, y) x + y end
function test()
end
test()
``````

`ERROR: MethodError: no method matching (::var"#add#4")(::Int64, ::Int64)`

The same thing happens if I define add as `function add(y) add(1, y) end`, and it doesn’t seem to help if I declare `global add` as the first line of test. Is this possible, or do I just need to use different names?

Hi and welcome!

The definition of `add` as a local name shadows all outer definitions.
To access any global identifier within a scope where that name is already taken, you can prepend them with the module name.
In your case, assuming you work in module Main:

``````function add(x, y) x + y end
function test()
end
test()
``````
2 Likes

Thanks!

That makes sense. In this instance it would be nice if local identifiers could overload ones from outer scopes, but I imagine that the trade-offs around default cases for scopes are fairly tricky.

That is, if I wish to use the outer `add` in `test()` the only options are either `add(x, y) = Main.add(x, y)` or `Main.add(3, 4)`? There’s no automatic way of having the inner `add` include all the overloads of the outer one?

(There’s no problem with this, I can just rename things or use `Main`. Just wanting to make sure I understand)

Thanks!

The problem here is that local `add` and `Main.add` are two different identifiers. So, the local `add` cannot possibly add overloaded behavior to `Main.add` within local context.
The local `add`, however, can be overloaded:

``````function add(x, y) x + y end
function test()
end
test() # returns (3, 1)
``````
2 Likes

I’m not sure what you want to achieve, but overloading a local function can be a way to build a function with multiple methods closing over some local state. For example:

``````function make_inc()
c = Ref(0)
inc(n) = c[]+=n

inc() = inc(1)

inc
end
``````
``````julia> const inc = make_inc()
inc (generic function with 2 methods)

julia> inc()
1

julia> inc()
2

julia> inc(3)
5
``````
2 Likes

Thanks, but not in this case. The use case is really just readability:

``````function helper(p1, p2, p3, v1, v2) ... end

function doer(p1, p2, p3)
helper(v1, v2) = Main.helper(p1, p2, p3, v1, v2)

helper(va, vb)
helper(vc, vd)
...
end
``````

(In retrospect, I probably should have put that in the first post)
{"ft_lang_label":"__label__en","ft_lang_prob":0.6294789,"math_prob":0.80257803,"size":442,"snap":"2020-10-2020-16","text_gpt3_token_len":128,"char_repetition_ratio":0.10502283,"word_repetition_ratio":0.0,"special_character_ratio":0.30316743,"punctuation_ratio":0.17757009,"nsfw_num_words":0,"has_unicode_error":false,"math_prob_llama3":0.95602846,"pos_list":[0,1,2],"im_url_duplicate_count":[null,null,null],"WARC_HEADER":"{\"WARC-Type\":\"response\",\"WARC-Date\":\"2020-04-02T06:54:19Z\",\"WARC-Record-ID\":\"<urn:uuid:2943b9ca-c3b0-4385-a37f-3d1187d95562>\",\"Content-Length\":\"23241\",\"Content-Type\":\"application/http; msgtype=response\",\"WARC-Warcinfo-ID\":\"<urn:uuid:10f22924-02af-4914-a92d-a2508b1db8c7>\",\"WARC-Concurrent-To\":\"<urn:uuid:745ecbb1-5b06-4c53-95c3-1189acb0fe6a>\",\"WARC-IP-Address\":\"72.52.80.20\",\"WARC-Target-URI\":\"https://discourse.julialang.org/t/overriding-methods-with-closures/36311\",\"WARC-Payload-Digest\":\"sha1:3EUF57A4TSKLYO4QNTWUH4ALKHG3TDUL\",\"WARC-Block-Digest\":\"sha1:ST53E3IH2PJHIQ25AJPU3XZCUQW5UF2V\",\"WARC-Identified-Payload-Type\":\"text/html\",\"warc_filename\":\"/cc_download/warc_2020/CC-MAIN-2020-16/CC-MAIN-2020-16_segments_1585370506673.7_warc_CC-MAIN-20200402045741-20200402075741-00259.warc.gz\"}"}