bug-make
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Proposition & PATCH: Add a "letrec" builtin function


From: Jouke Witteveen
Subject: Re: Proposition & PATCH: Add a "letrec" builtin function
Date: Sun, 12 Jan 2025 17:20:42 +0100

On Sat, Jan 11, 2025 at 3:40 AM Pete Dietl <petedietl@gmail.com> wrote:
> You need a recursive let if you want to be able to define inner functions, 
> like a helper function.

That much I understand, but I cannot come up with many scenarios where
that would make sense in Make. Whenever the definition of the inner
function/macro is evaluated, the values of all the arguments it will
be called with are already known and the call will happen in the same
evaluation! Maybe you want to define an inner function that uses
recursion. In that case, it may offer something new, but note that GNU
Make has $(foreach ...), but not $(while ...). I guess if you want
recursion, some form of a while loop may be more beautiful. I don't
know what a good signature would be, though.

Regards,
- Jouke

> On Mon, Dec 30, 2024, 5:21 AM Jouke Witteveen <j.witteveen@gmail.com> wrote:
>>
>> Hi Pete,
>>
>> On Thu, Dec 26, 2024 at 7:44 AM Pete Dietl <petedietl@gmail.com> wrote:
>> > I propose adding a "letrec" builtin to complement the "let" builtin.
>> > The "let" builtin does not allow one to define inner functions or
>> > mutually recursive definitions.
>>
>> Can you maybe help me understand why this functionality would be
>> desirable? Sure, recursively expanded variables with a limited scope
>> could be a thing, but I fail to see what functionality they would
>> offer. The way I see it, recursively expanded variables are mainly
>> useful when you don't know all the values of the variables referenced,
>> which is exactly not the case when you limit the scope.
>>
>> > Variable names and their values are provided pairwise. "Letrec" strips
>> > any leading whitespace from the expansion of each variable name
>> > argument.
>>
>> Your suggestion does not do any kind of multiple assignment (I modeled
>> `let` a bit after `read`), so it does not need to have a variable
>> number of arguments and could just be
>>   $(letrec NAME,MACRO,EXPRESSION)
>> and, apart from nested bindings, the main use would be
>>   $(letrec NAME,MACRO,$(call NAME,PARAM))
>> which is equivalent to just MACRO with $1 replaced by PARAM.
>>
>> > Here is an example Makefile using the new function:
>> >
>> > print-var = $(info $$($1) = '$($(1))')
>> >
>> > $(letrec \
>> >          a,foo, \
>> >          b,bar, \
>> >          c,$(call double,~hello~), \
>> >          double,$(1)$(1), \
>> >     $(call print-var,a) \
>> >     $(call print-var,b) \
>> >     $(call print-var,c) \
>> >     $(info 2 x $$(a) = '$(call double,$(a))') \
>> >   )
>>
>> In your example, you don't need `letrec` for `a` or `b` and all I see
>> is a roundabout way of writing
>>   $(foreach x,foo ~hello~,$(info $(x) $(x)))
>>
>> Regards,
>> - Jouke



reply via email to

[Prev in Thread] Current Thread [Next in Thread]