Re: [Python-ideas] As-do statements/anonymous blocks in python

2018-07-28 Thread Greg Ewing

James Lu wrote:

as expr [do comma-separated-expressions]:

>block


means evaluate expr, then call the result of the expression. If do is
present, call it with the argument list after do.


This kind of thing has been proposed before. Although it seems
like a straightforward idea, there are some thorny edge cases
concerning how things like 'return' and 'break' in the code
block should be handled. For example, what should this do:

   def f():
  as g:
 return

Should that return from g or from f?

Or this:

   while some_codition:
  as g:
 if some_other_condition:
break

If you want to flesh out your proposal you will have to address
these. Also you should seek out previous discussions about code
blocks to make sure you're not just rehashing old ground.

--
Greg




 Otherwise, call it with no

arguments.


If you don't have practical uses, this proposal has ZERO chance of being 
accepted.



I have already shown a Flask use case and another poster has mentioned they
would find it useful in their own code. (Though they had reservations on
whether it should be included in Python.)

I simply said I wasn’t totally aware of all practical use cases, especially
practical abuse cases. ___ 
Python-ideas mailing list Python-ideas@python.org 
https://mail.python.org/mailman/listinfo/python-ideas Code of Conduct:

http://python.org/psf/codeofconduct/


___
Python-ideas mailing list
Python-ideas@python.org
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/


Re: [Python-ideas] As-do statements/anonymous blocks in python

2018-07-28 Thread Jonathan Fine
Hi James

This is an attempt to respond to the issues that be lying behind your
request for code blocks in Python. It's my two cents worth
(https://en.wikipedia.org/wiki/My_two_cents) of opinion.

I really do wish we could have language that had all of Ruby's
strengths, and also all of Python's. That would be really nice. Quite
something indeed.

But most strengths, in another situation, can be a weakness. Language
design is often a compromise between conciseness and readability, ease
of use and performance, good for beginners and good for experts, and
many other factors. Such as innovation and stability.

Guido's decisions, as BDFL, have shaped Python and its community into
what it is now. It is one set of compromises. Other languages, such as
Ruby, have made different compromises. Now that the BDFL is on
vacation, the challenge is to maintain the essence of Python while
continuing to innovate.

Python's compromises and implementation give the language a large sweet spot.
===
https://en.wikipedia.org/wiki/Sweet_spot_(sports)
The sweet spot is a place where a combination of factors results in a
maximum response for a given amount of effort.
===

Languages do influence each other. Ruby is good at internal Domain
Specific Languages (DSLs). And there's Perrotta's influential book on
Ruby Metaprogramming. That's something I think Python could learn
from.

But I don't see any need (or even benefit) in adding new language
features to Python, so it can do better at DSLs. It's fairly easy to
write a decorator that turns a class into a dictionary of 'code
blocks'. I think that might be what you really want.

I'd be pleased to hear what you have to say about this.

with best regards

Jonathan
___
Python-ideas mailing list
Python-ideas@python.org
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/


Re: [Python-ideas] As-do statements/anonymous blocks in python

2018-07-28 Thread James Lu
By passing a function to another function I meant passing a code block as an 
inline function to a function call.

The do statement is simply the arguments the function is called with

Brackets = optional
as expr [do comma-separated-expressions]:
block

means evaluate expr, then call the result of the expression. If do is present, 
call it with the argument list after do. Otherwise, call it with no arguments. 

> If you don't have practical uses, this proposal has ZERO chance of being
> accepted.

I have already shown a Flask use case and another poster has mentioned they 
would find it useful in their own code. (Though they had reservations on 
whether it should be included in Python.)

I simply said I wasn’t totally aware of all practical use cases, especially 
practical abuse cases. 
___
Python-ideas mailing list
Python-ideas@python.org
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/


Re: [Python-ideas] As-do statements/anonymous blocks in python

2018-07-27 Thread Steven D'Aprano
I *think* you are trying to find a syntax for "code blocks" like Ruby
has, but I'm not sure. Your examples are a little confusing to me 
(possibly because you have at least three separate suggestions here, 
"as" blocks, a mysterious "do" keyword I don't understand, and partial 
application using % as argument placeholder).

Many people have tried to find a syntax for code block expressions, none 
have succeeded. Please note that being an *expression* is critical. We 
already have syntax for code block statements, it is the "def" keyword.

You probably ought to spend a few days searching the mailing list 
archives for previous discussions before you get your hopes up.

Before I spend any more time on this proposal, I'll skip right to the
end of your post:


On Wed, Jul 25, 2018 at 01:07:50PM -0400, James Lu wrote:
 
> I’m not totally sure of practical uses,

If you don't have practical uses, this proposal has ZERO chance of being
accepted.

Sometimes we can't get proposals accepted even with practical uses.


> but I’m imagining it would make
> passing a function to another function much more convenient.

I don't see how it can be more convenient than:

function(another_function)



-- 
Steve
___
Python-ideas mailing list
Python-ideas@python.org
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/


Re: [Python-ideas] As-do statements/anonymous blocks in python

2018-07-26 Thread Steven D'Aprano
On Thu, Jul 26, 2018 at 02:07:07PM +0200, Michel Desmoulin wrote:

> 4 - introducing a new keyword is the hardest thing you can ever ask on
> this list.

Introducing a new keyword is like falling off a log compared to 
introducing a new operator.

-- 
Steve
___
Python-ideas mailing list
Python-ideas@python.org
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/


Re: [Python-ideas] As-do statements/anonymous blocks in python

2018-07-26 Thread Robert Vanden Eynde
> lumberjack(15, %)
> # is equivalent to the expression
> lambda x: lumberjack(15, %)

You mean lambda x: lumberjack(15, x) ?

So you'd want a better syntax for functools.partial, here your example is
partial(lumberjack, 15).

However this syntax you allow to write lumberjack(%, 15) which is only
possible with partial using keyword arguments, like lumberjack (y=15)
(given that the second argument is called "y") and in that case I know at
least one library on pip doing the job with Ellipsis :

from funcoperators import elipartial
elipartial(lumberjack, ..., 15)
# gives lambda x: lumberjack (x, 15)

elipartial (lumberjack, ..., 15, ..., 12, ...)
# gives lambda x, y, z: lumberjack(x, 15, y, 12, z)

And the lib even provide a decorator to have that kind of syntax using "[" :

partially(lumberjack)[15]
would be the same as partial(lumberjack, 15)

So, that functionality does really need new syntax.


Le jeu. 26 juil. 2018 à 14:07, Michel Desmoulin 
a écrit :

> I like the concept, and I several times wished I could have had a
> reference to the block of code in a `with` clause.
>
> However, it is unlikely to happen:
>
> 1 - Guido restricted lambda to one expression, and this would just be a
> way around that
>
> 2 - This will be tempting to use for callbacks and chaining things,
> leading to the nesting hell we tried very carefully to avoid fom other
> languages. The example for sorted is also kinda twisted.
>
> 3 - Most of the example (and you show it yourself with flask) are
> already possible with a more verbose syntaxe based on decorators. Example:
>
>
> @atexit.register
> def _():
> print('Goodbye')
>
> 4 - introducing a new keyword is the hardest thing you can ever ask on
> this list.
>
>
>
> Le 25/07/2018 à 19:07, James Lu a écrit :
> > I'm open to any changes or criticism.
> >
> > ```
> > import atexit
> > as atexit.register:
> > # ...do various cleanup tasks...
> > print('Goodbye')
> >
> > # is approximately equivalent to =>
> > import atexit
> > def _():
> > # ...do various cleanup tasks...
> > print('Goodbye')
> > atexit.register(_)
> >
> > # flask example
> > @app.route("/")
> > def hello():
> > return "Hello World!"
> > # is approximately equivalent to =>
> > as app.route('/'):
> > return "Hello World!"
> >
> > @app.route('/user/')
> > def show_user_profile(username):
> > # show the user profile for that user
> > return 'User %s' % username
> >
> > as app.route('/user/') do username:
> > return "Hello World!"
> >
> > def print_sorted(iterable, block):
> > sorted(iterable, )
> >
> > l = [1, 2, 3, 4, 'spam']
> >
> > as l.sort(key=%) do obj:
> > return str(obj)
> >
> > # multiple arguments
> > as spam do a, b:
> > ...
> > ```
> > ## `%`  function call syntax
> > Calling a function with a single percent in place of an argument creates
> > a new function.
> >
> > ```
> > lumberjack(15, %)
> > # is equivalent to the expression
> > lambda x: lumberjack(15, %)
> > ```
> > Using `*` instead of `%` could also be possible.
> >
> > ```
> > import threading, time
> > def interval(seconds, block):
> > def target():
> > while True:
> > time.sleep(seconds)
> > if block():  # stop looping if block returns True
> > break
> > threading.Thread(target=target).start()
> >
> > as interval(5, %):
> >print("chirp")
> > # => chirp every 5 seconds on a seperate thread
> > as threading.Timer(5, %):
> >print("hi")
> > # => say "hi" in 5 seconds
> > ```
> >
> > ## `^` currying function definition syntax?
> > I'm not sure this is necessary or a good idea.
> > ```
> > def interval(seconds, ^block):
> > def target():
> > while True:
> > time.sleep(seconds)
> > if block():  # stop looping if block returns True
> > break
> > threading.Thread(target=target).start()
> > # is aprroximately equivalent to
> > def interval(seconds, block=None):
> > def inner(block):
> > def target():
> > while True:
> > time.sleep(seconds)
> > if block():
> > break
> > threading.Thread(target=target).start()
> > if block == None:
> > def outer(block):
> > return inner(block)
> > else:
> > return inner(block)
> >
> > as interval(5):
> > print('chirp')
> > # equivalent to
> > interval(5)(lambda: print('chirp'))
> > ```
> > ### Lazy evaluation of chained `%` calls?
> > This would allow things like:
> > ```
> > start_on_new_thread = threading.Thread(target=%).start()
> > def bong():
> > while True:
> > time.sleep(6*60)
> > print('BONG')
> > start_on_new_thread(bong)
> > # alternatively
> > as start_on_new_thread:
> > while True:
> > time.sleep(6*60)
> > print('BONG')
> > ```
> >
> > ## As-do statements in classes
> > ```
> > class M():
> >  def __init__(self):
> >  self.time = 5
> >  as 

Re: [Python-ideas] As-do statements/anonymous blocks in python

2018-07-26 Thread Michel Desmoulin
I like the concept, and I several times wished I could have had a
reference to the block of code in a `with` clause.

However, it is unlikely to happen:

1 - Guido restricted lambda to one expression, and this would just be a
way around that

2 - This will be tempting to use for callbacks and chaining things,
leading to the nesting hell we tried very carefully to avoid fom other
languages. The example for sorted is also kinda twisted.

3 - Most of the example (and you show it yourself with flask) are
already possible with a more verbose syntaxe based on decorators. Example:


@atexit.register
def _():
print('Goodbye')

4 - introducing a new keyword is the hardest thing you can ever ask on
this list.



Le 25/07/2018 à 19:07, James Lu a écrit :
> I'm open to any changes or criticism.
> 
> ```
> import atexit
> as atexit.register:
>     # ...do various cleanup tasks...
>     print('Goodbye')
> 
> # is approximately equivalent to => 
> import atexit
> def _():
>     # ...do various cleanup tasks...
>     print('Goodbye')
> atexit.register(_)
> 
> # flask example
> @app.route("/")
> def hello():
>     return "Hello World!"
> # is approximately equivalent to =>
> as app.route('/'):
>     return "Hello World!"
> 
> @app.route('/user/')
> def show_user_profile(username):
>     # show the user profile for that user
>     return 'User %s' % username
> 
> as app.route('/user/') do username:
>     return "Hello World!"
> 
> def print_sorted(iterable, block):
>     sorted(iterable, )
> 
> l = [1, 2, 3, 4, 'spam']
> 
> as l.sort(key=%) do obj:
>     return str(obj)
> 
> # multiple arguments
> as spam do a, b:
>     ...
> ```
> ## `%`  function call syntax
> Calling a function with a single percent in place of an argument creates
> a new function. 
> 
> ```
> lumberjack(15, %)
> # is equivalent to the expression
> lambda x: lumberjack(15, %)
> ```
> Using `*` instead of `%` could also be possible.
> 
> ```
> import threading, time
> def interval(seconds, block):
>     def target():
>         while True:
>             time.sleep(seconds)
>             if block():  # stop looping if block returns True
>                 break
>     threading.Thread(target=target).start()
> 
> as interval(5, %):
>    print("chirp")
> # => chirp every 5 seconds on a seperate thread
> as threading.Timer(5, %):
>    print("hi")
> # => say "hi" in 5 seconds
> ```
> 
> ## `^` currying function definition syntax?
> I'm not sure this is necessary or a good idea.
> ```
> def interval(seconds, ^block):
>     def target():
>         while True:
>             time.sleep(seconds)
>             if block():  # stop looping if block returns True
>                 break
>     threading.Thread(target=target).start()
> # is aprroximately equivalent to
> def interval(seconds, block=None):
>     def inner(block):
>         def target():
>             while True:
>                 time.sleep(seconds)
>                 if block():
>                     break
>         threading.Thread(target=target).start()
>     if block == None:
>         def outer(block):
>             return inner(block)
>     else:
>         return inner(block)
> 
> as interval(5):
>     print('chirp')
> # equivalent to 
> interval(5)(lambda: print('chirp'))
> ```
> ### Lazy evaluation of chained `%` calls?
> This would allow things like:
> ```
> start_on_new_thread = threading.Thread(target=%).start()
> def bong():
>     while True:
>         time.sleep(6*60)
>         print('BONG')
> start_on_new_thread(bong)
> # alternatively
> as start_on_new_thread:
>     while True:
>         time.sleep(6*60)
>         print('BONG')
> ```
> 
> ## As-do statements in classes
> ```
> class M():
>      def __init__(self):
>          self.time = 5
>      as interval(self.time, %):
>          print('chirp')
> ```
> 
> I'm not sure if this should be valid, and I'd like the community's input
> on when as-do statements should be bound when as-do.
> 
> ## Proposed Type Hinting Syntax
> ```
> as app.route('/user/') do (username: str): 
>     return "Hello World!"
> ```
> 
> Alternatives:
> ```
> as app.route('/user/') do username: str%
>     return "Hello World!"
> # like objective-c
> as app.route('/user/') do username: str^
>     return "Hello World!"
> # like coffeescript
> as app.route('/user/') do username: str ->
>     return "Hello World!"
> ```
> 
> I’m not totally sure of practical uses, but I’m imagining it would make
> passing a function to another function much more convenient. In React,
> you pass an argument called `render` to a `FlatList`, and `render`
> renders an item of the list. `FlatList` is a scrollable list that
> handles unloading off-screen items and loading items that will appear in
> the scroll box soon.
> 
> 
> ___
> Python-ideas mailing list
> Python-ideas@python.org
> https://mail.python.org/mailman/listinfo/python-ideas
> Code of Conduct: http://python.org/psf/codeofconduct/
> 

Re: [Python-ideas] As-do statements/anonymous blocks in python

2018-07-26 Thread Rhodri James

On 25/07/18 18:07, James Lu wrote:

I'm open to any changes or criticism.

```
import atexit
as atexit.register:
 # ...do various cleanup tasks...
 print('Goodbye')

# is approximately equivalent to =>
import atexit
def _():
 # ...do various cleanup tasks...
 print('Goodbye')
atexit.register(_)

# flask example
@app.route("/")
def hello():
 return "Hello World!"
# is approximately equivalent to =>
as app.route('/'):
 return "Hello World!"


Could you explain what you expect "as" to do *in words* please?  These 
two examples give me conflicting ideas of what you mean.


--
Rhodri James *-* Kynesim Ltd
___
Python-ideas mailing list
Python-ideas@python.org
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/