March 27, 2014
On 2014-03-27 14:45, monarch_dodra wrote:
> On Thursday, 27 March 2014 at 14:41:19 UTC, Brian Rogoff wrote:
>> On Thursday, 27 March 2014 at 13:23:27 UTC, monarch_dodra wrote:
>>> On Thursday, 27 March 2014 at 12:48:41 UTC, Simen Kjærås wrote:
>>>> Your new fold (foldl? Should we have foldr as well?)
>>>
>>> "fold" (from what I understood) is what you call "foldl". It was
>>> discussed to not introduce "foldr", as it's just
>>> "fold!(binaryReverseArgs!Fun)(range.retro);".
>>>
>>> I'm not sure I was able to understand what the difference between
>>> "fold" and "foldl" is...
>>
>> In functional languages,
>>
>> fold_left(f, a, [b1, ..., bn]) is
>> f((... (f, (f, a, b1), b2) ...), bn)
>>
>> as you can see, the innermost f call is on the leftmost sequence
>> element, and
>>
>> fold_right(f, [a1, ..., an], b) is
>> f(a1, (f a2 (... f(an, b) ...)))
>>
>> That's how I think of them.
>
> Right, but what about "fold" vs "fold_left"? Is there a difference?

Different languages may have different standards, but I think fold is usually a left fold. So, no difference.

--
  Simen
March 27, 2014
On 2014-03-27 16:35, Meta wrote:
> On Thursday, 27 March 2014 at 16:33:53 UTC, monarch_dodra wrote:
>> Also yes, but the general feeling around here, is that "string
>> functions" are a thing of the past, and should be replaced by "real"
>> lambda functions.
>>
>> As such, even if "naryFun" works, it promotes the use of something
>> that is unpopular, and that some would like to see disappear.
>
> Don't forget this use case:
>
> //Error
> alias fun = (a) => a + 1;
>
> //Ok
> alias fun = unaryFun!(a => a + 1);
>
> This is the main reason I think naryFun is a good idea.

That could very well be argued to be a bug, though.

--
  Simen
March 27, 2014
On 2014-03-27 16:33, monarch_dodra wrote:
> On Thursday, 27 March 2014 at 15:54:46 UTC, Simen Kjærås wrote:
>> On 2014-03-27 15:33, Meta wrote:
>> Is it even necessary to specifically have a binary version of that?
>> This seems to be a working generalization of binaryReverseArgs:
>
> In binaryReverseArgs's defense, it was written before "Reverse!". But
> yes, it's just a question of time before binaryReverseArgs is replaced.
>
> It's just a matter of having someone tackle the issue and submit a
> proposal *hint* ;)

Done:
https://github.com/D-Programming-Language/phobos/pull/2054


>> On the same note, binaryFun and unaryFun seem to me unnecessary
>> specializations of a more general 'fun' template. Philippe Sigaud has
>> an implementation in his dranges called naryFun
>> (https://github.com/PhilippeSigaud/dranges). That code has apparently
>> not been touched for at least two years, so YMMV.
>
> Also yes, but the general feeling around here, is that "string
> functions" are a thing of the past, and should be replaced by "real"
> lambda functions.
>
> As such, even if "naryFun" works, it promotes the use of something that
> is unpopular, and that some would like to see disappear.

True.

--
  Simen
March 27, 2014
On Thursday, 27 March 2014 at 16:42:31 UTC, Simen Kjærås wrote:
> That could very well be argued to be a bug, though.
>
> --
>   Simen

What is the bug? Alias aliases symbols. A function literal is not a symbol, but a template instantiation is. Therefore, wrapping a function literal in a template instantiation allows it to be aliased. I don't think there's any bugger behaviour here.
March 27, 2014
On Thursday, 27 March 2014 at 17:21:14 UTC, Meta wrote:
> On Thursday, 27 March 2014 at 16:42:31 UTC, Simen Kjærås wrote:
>> That could very well be argued to be a bug, though.
>>
>> --
>>  Simen
>
> What is the bug? Alias aliases symbols. A function literal is not a symbol, but a template instantiation is. Therefore, wrapping a function literal in a template instantiation allows it to be aliased. I don't think there's any bugger behaviour here.

Whoops, I mean buggy.
March 27, 2014
On 2014-03-27 17:21, Meta wrote:
> On Thursday, 27 March 2014 at 16:42:31 UTC, Simen Kjærås wrote:
>> That could very well be argued to be a bug, though.
>>
>> --
>>   Simen
>
> What is the bug? Alias aliases symbols. A function literal is not a
> symbol, but a template instantiation is. Therefore, wrapping a function
> literal in a template instantiation allows it to be aliased. I don't
> think there's any bugger behaviour here.

Ah, true. Call it an enhancement request, then. Wanting to alias a function literal like that is so common the language should support it.

--
  Simen
March 27, 2014
On Thursday, 27 March 2014 at 17:30:58 UTC, Simen Kjærås wrote:
> Ah, true. Call it an enhancement request, then. Wanting to alias a function literal like that is so common the language should support it.
>
> --
>   Simen

It's a bit unintuitive as to what works and what doesn't (although it makes sense for the most part).

//No good
alias fun = a => a + 1;
alias fun = (int a) => a + 1;
//Ok
alias fun = unaryFun!(a => a + 1);
alias fun = unaryFun!((int a) => a + 1);

//Doesn't work
enum fun = a => a + 1;
enum fun = unaryFun!(a => a + 1);
//Works
enum fun = (int a) => a + 1;
enum fun = unaryFun!((int a) => a + 1);


But the fun is just beginning. Now we can mix in template aliases and enums.

//Chokes
alias fun() = a => a + 1;
alias fun() = (a => a + 1);
alias fun() = (int a) => a + 1;
alias fun(T) = a => a + 1;
alias fun(T) = (a => a + 1);
alias fun(T) = (int a) => a + 1;

//Fine
alias fun() = unaryFun!(a => a + 1);

//Compiles but fails when fun is called
alias fun() = unaryFun!((int a) => a + 1);
fun(1); //undefined reference to `_D4f2924mainFZv8__T3funZ9__lambda2FNaNbNfiZi'

enum fun() = unaryFun!(a => a + 1);
fun(1); //cannot infer type from template template __lambda2

enum fun() = unaryFun!((int a) => a + 1);
fun(1); //cannot deduce function from argument types !()(int)

enum fun() = a => a + 1;
fun(1); //type void is inferred from initializer a => a + 1

enum fun() = (int a) => a + 1;
fun(1); //cannot deduce function from argument types !()(int)


So there you have it.




March 27, 2014
On 03/27/2014 03:45 PM, monarch_dodra wrote:
>
> Right, but what about "fold" vs "fold_left"? Is there a difference?

'fold' is not descriptive enough. Ranges/lists have a very particular structure allowing 'foldl' to make sense. In general recursive data types (eg. think binary tree) allow only one fold (the recursive one). The instantiation for lists is 'foldr'.

I'd rather have this named 'foldl'. 'fold' is a more abstract name 'foldr' rather than 'foldl'.
March 27, 2014
On 03/27/2014 07:04 PM, Meta wrote:
>
> It's a bit unintuitive as to what works and what doesn't (although it
> makes sense for the most part).

It doesn't make sense at all. It is an arbitrary limitation. The rule is simple though: One can only alias things that syntactically look like they might be types. This is why the following triviality is way more useful than it should be:

alias Id(alias a)=a;

alias fun = Id!(a=>a); // ok!
March 28, 2014
On Thursday, 27 March 2014 at 22:33:50 UTC, Timon Gehr wrote:
> It doesn't make sense at all. It is an arbitrary limitation. The rule is simple though: One can only alias things that syntactically look like they might be types. This is why the following triviality is way more useful than it should be:
>
> alias Id(alias a)=a;
>
> alias fun = Id!(a=>a); // ok!

You can tell me that function literals look like types, but I won't believe you.