Re: Layers of abstraction, was Re: RFC: Proposal: Deterministic Object Destruction

2018-03-06 Thread Ooomzay
On Wednesday, 7 March 2018 06:43:10 UTC, Ooomzay  wrote:
> On Tuesday, 6 March 2018 14:12:38 UTC, Peter Otten  wrote:
> > Chris Angelico wrote:
> > 
> > > On Tue, Mar 6, 2018 at 10:04 AM, Steven D'Aprano
> > >  wrote:
> > >> # Later.
> > >> if __name__ = '__main__':
> > >> # Enter the Kingdom of Nouns.
> > > 
> > > Don't you need a NounKingdomEnterer to do that for you?
> > 
> > No, for some extra flexibility there should be a NounKingdomEntererFactory 
> 
> For example open().
> 
> > -- which of course has to implement the AbstractNounKingdomEntererFactory 
> > interface. 
> 
> For example a PEP 343 "Context Manager".
> 
> In the swamplands of the pythonistas the one-eyed man is BDFL!
> 
> Amen.

Damn. That should have read:-

In the swamplands of the pythonistas the man with a badly leaking boat is BDFL.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Layers of abstraction, was Re: RFC: Proposal: Deterministic Object Destruction

2018-03-06 Thread Ooomzay
On Tuesday, 6 March 2018 14:12:38 UTC, Peter Otten  wrote:
> Chris Angelico wrote:
> 
> > On Tue, Mar 6, 2018 at 10:04 AM, Steven D'Aprano
> >  wrote:
> >> # Later.
> >> if __name__ = '__main__':
> >> # Enter the Kingdom of Nouns.
> > 
> > Don't you need a NounKingdomEnterer to do that for you?
> 
> No, for some extra flexibility there should be a NounKingdomEntererFactory 

For example open().

> -- which of course has to implement the AbstractNounKingdomEntererFactory 
> interface. 

For example a PEP 343 "Context Manager".

In the swamplands of the pythonistas the one-eyed man is BDFL!

Amen.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: LXML: can't register namespace

2018-03-06 Thread Steven D'Aprano
On Tue, 06 Mar 2018 23:03:15 -0500, Andrew Z wrote:

> Hello,
>  with 3.6 and latest greatest lxml:
> 
> from lxml import etree
> 
> tree = etree.parse('Sample.xml')
> etree.register_namespace('','http://www.example.com')

> it seems to not be happy with the empty tag . But i'm not sure why and
> how to go about it.

Have you tried using something other than the empty string?

In the interactive interpreter, what does 

help(etree.register_namespace) 

say?



-- 
Steve

-- 
https://mail.python.org/mailman/listinfo/python-list


LXML: can't register namespace

2018-03-06 Thread Andrew Z
Hello,
 with 3.6 and latest greatest lxml:

from lxml import etree

tree = etree.parse('Sample.xml')
etree.register_namespace('','http://www.example.com')

causes:
Traceback (most recent call last):
  File "/home/az/Work/flask/tutorial_1/src/xml_oper.py", line 16, in

etree.register_namespace('','http://www.example.com')
  File "src/lxml/etree.pyx", line 203, in lxml.etree.register_namespace
(src/lxml/etree.c:11705)
  File "src/lxml/apihelpers.pxi", line 1631, in lxml.etree._tagValidOrRaise
(src/lxml/etree.c:35382)
ValueError: Invalid tag name ''

partial Sample.xml:


http://www.example.com";>
 
  



it seems to not be happy with the empty tag .
But i'm not sure why and how to go about it.

thank you
AZ
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Subprocess Startup Error

2018-03-06 Thread Terry Reedy

On 3/6/2018 6:00 PM, Jeremy Jamar St. Julien wrote:

Whenever I try to open the python shell it says IDLE’s subprocess didn’t make a 
connection.


You must be referring to IDLE's GUI Shell, not Python's normal console 
text (TUI?) shell or REPL.


IDLE normally runs its GUI in one process and your code in another 
process, connected by a socket.  The message means that the socket 
connection failed.


Everything worked fine yesterday and I haven’t done anything I think 
would cause this problem.


Something has done something somewhere.

Any way to fix this? I’ve tried repairing and redownloading

Start IDLE in a console with python -m idlelib (idlelib.idle on 2.7) and 
you *may* get an exception or other error message that explains the 
situation.  There are 5 to 10 known possible reasons.


What python binary are you running IDLE with?  (It is displayed on the 
first line of output when you start.)  Start normally and look, then 
start in the console and look, to make sure you are running the same 
Python both times.


--
Terry Jan Reedy


--
https://mail.python.org/mailman/listinfo/python-list


Subprocess Startup Error

2018-03-06 Thread Jeremy Jamar St. Julien
Whenever I try to open the python shell it says IDLE’s subprocess didn’t make a 
connection. Everything worked fine yesterday and I haven’t done anything I 
think would cause this problem. Any way to fix this? I’ve tried repairing and 
redownloading
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: RFC: Proposal: Deterministic Object Destruction

2018-03-06 Thread Steven D'Aprano
On Tue, 06 Mar 2018 14:09:53 -0800, Ooomzay wrote:

> Unfortunately, despite having conquered it, without a _guarantee_ of
> this behaviour from the language, or at least one mainstream
> implementation, I will not invest in python again.

Oh well, so sad. See you later.


-- 
Steve

-- 
https://mail.python.org/mailman/listinfo/python-list


Re: RFC: Proposal: Deterministic Object Destruction

2018-03-06 Thread Chris Angelico
On Wed, Mar 7, 2018 at 9:09 AM, Ooomzay  wrote:
>> I'm not trying to dissuade you from using RAII in your own applications,
>> if it works for you, great.
>
> Unfortunately, despite having conquered it, without a _guarantee_ of this
> behaviour from the language, or at least one mainstream implementation,
> I will not invest in python again. Nor recommend any one else with a serious
> real world resource management application to do so. This was the original
> motive for my PEP.

What a pity Python will have to lose someone whose sole goal was to
write C++ code. Had you but chosen to write Python code instead, you
could have saved us all a hundred emails or so and just used the
'with' statement, same as the rest of us do. Considering that "real
world resource management" is *exactly* the purpose of the 'with'
statement, I honestly don't see what the problem is.

ChrisA
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Bitstream -- Binary Data for Humans

2018-03-06 Thread Roel Schroeven

Sébastien Boisgérault schreef op 6/03/2018 10:23:
I had a look at the AIS message format from your link(https://en.wikipedia.org/wiki/Automatic_identification_system#Message_format) and this seems to be a nice use case; all the data components seem to be nicely aligned on the byte boundary ... until you see that the payload uses ASCII6(*), which I didn't know about. 


Thanks again for the info!


ASCII6 is only the first layer where your Bitstream could be useful. 
It's the easy part :).


The main work comes after that: decoding ASCII6 results in binary data 
which we need to decode into AIS messages. You can see the most 
important ones at https://navcen.uscg.gov/?pageName=AISMessagesA and 
https://navcen.uscg.gov/?pageName=AISMessagesAStatic but there are many 
more.


So for each message we first extract the first 6 bits, which tells us 
the message identifier. What we need to do afterwards depends on that 
message identifier. The links above describe how to deal with messages 
1, 2 and 3 (they are identical except for the message identifier; I 
don't know why there are 3 instead of just one) and 5. Basically it's 
things like 2 bits for this, next 30 bits for that, etc. That's where 
I'm hoping your Bitstream can really shine.


Also note, but now I'm getting off topic,  that we don't have to deal 
with the low-level data as is described in your link: that is handled by 
the AIS transponder or AIS receiver, from which we receive it using 
simple NMEA 0183 serial sentences: see 
https://en.wikipedia.org/w/index.php?title=NMEA_0183&oldid=828034316#Message_structure


--
The saddest aspect of life right now is that science gathers knowledge
faster than society gathers wisdom.
  -- Isaac Asimov

Roel Schroeven

--
https://mail.python.org/mailman/listinfo/python-list


Re: RFC: Proposal: Deterministic Object Destruction

2018-03-06 Thread Ooomzay

On Monday, 5 March 2018 23:06:53 UTC, Steven D'Aprano  wrote:
> On Mon, 05 Mar 2018 09:22:33 -0800, Ooomzay wrote:
> [...]
> > If you would like to have a shot at coding this without RAII, but
> > preserving the OO design, you will find that it is considerably
> > simpler than the with/context manager approach.
> 
> Preserving the OO design, you say? Okay, since my application apparently 
> isn't allowed to know that it is processing two files, I'll simply 
> delegate that to the object:
> 
> class C(A, B):
> def run(self):
> with open(self.a) as a:
> with open(self.b) as b:
> process(a, b)
> 
> # Later.
> if __name__ = '__main__':
> # Enter the Kingdom of Nouns.
> c = C()
> c.run()
> 
> There you go. Encapsulation and OO design.

1. This does not execute. It is only when you actually flesh out 
these deliberately minimal classes A, B & C with PEP232 paraphernalia
that we all be able to see clearly how much cleaner or messier 
things are with PEP232. 

2. Your Class C breaks A & B's encapsulation by inheriting rather than 
composing them. Apart from increasing coupling and preventing 
substitution, C contained A & B in this example to illustrate that there is 
no RAII related burden whatever_on this intermediate class as 
it manages no external resources directly. It does not even 
need to implement __del__.

3. You have assumed a single threaded application. Please imagine 
that A and B are classes managing some remote valves and maintain 
their own threads as well as a serial port for comms. And C is there to 
coordinate them towards some greater purpose.

If you would like to try and add PEP232 support to
classes A,B & C to the point that you can create
and destroy c = C() in an exception-safe way we may 
all learn something.

> I'm not trying to dissuade you from using RAII in your own applications, 
> if it works for you, great.

Unfortunately, despite having conquered it, without a _guarantee_ of this 
behaviour from the language, or at least one mainstream implementation, 
I will not invest in python again. Nor recommend any one else with a serious 
real world resource management application to do so. This was the original 
motive for my PEP.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Peter Otten
Chris Angelico wrote:

> On Wed, Mar 7, 2018 at 2:12 AM, Kirill Balunov 
> wrote:
>>
>>
>> 2018-03-06 17:55 GMT+03:00 Chris Angelico :
>>>
>>> On Wed, Mar 7, 2018 at 1:48 AM, Kirill Balunov 
>>> wrote:
>>> > Note: For some historical reasons as the first argument you can use
>>> > None instead of function, in this case the identity function is
>>> > assumed. That is, all elements of iterable that are false are removed
>>> > which is equivalent
>>> > to (item for item in iterable if item). Currently, for the same
>>> > purpose the
>>> > preferred form is `filter(bool, iterable)`.
>>> >
>>>
>>> I'd prefer to word it something like:
>>>
>>> If the first argument is None, the identity function is assumed. That
>>> is, all elements of the iterable that are false are removed; it is
>>> equivalent to (item for item in iterable if item). It is approximately
>>> equivalent to (but faster than) filter(bool, iterable).
>>>
>>> ChrisA
>>> --
>>> https://mail.python.org/mailman/listinfo/python-list
>>
>>
>> I do not want to seem rude and stubborn, but how much faster is it to
>> highlight or emphasize it:
>>
> 
> Timings mean little. Why do we write:
> 
> if lst:
> 
> instead of:
> 
> if bool(lst):
> 
> ? Because it's unnecessary and pointless to call bool() on something
> before using it in a boolean context. If that concept causes you
> problems, it's not the fault of the filter function; filter simply
> uses something in a boolean context.
> 
> So "the identity function" is more correct than "the bool() function".

Fun fact: CPython handles filter(bool) and filter(None) the same way, it 
sets the checktrue flag and chooses the fast path:

static PyObject *
filter_next(filterobject *lz)
{
PyObject *item;
PyObject *it = lz->it;
long ok;
PyObject *(*iternext)(PyObject *);
int checktrue = lz->func == Py_None || lz->func == (PyObject 
*)&PyBool_Type;

iternext = *Py_TYPE(it)->tp_iternext;
for (;;) {
item = iternext(it);
if (item == NULL)
return NULL;

if (checktrue) {
ok = PyObject_IsTrue(item);
} else {
PyObject *good;
good = PyObject_CallFunctionObjArgs(lz->func, item, NULL);
if (good == NULL) {
Py_DECREF(item);
return NULL;
}
ok = PyObject_IsTrue(good);
Py_DECREF(good);
}
if (ok > 0)
return item;
Py_DECREF(item);
if (ok < 0)
return NULL;
}
}

If there were a built-in identity() function it could be treated the same 
way.


-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Chris Angelico
On Wed, Mar 7, 2018 at 2:33 AM, Kirill Balunov  wrote:
>
>
> 2018-03-06 17:55 GMT+03:00 Chris Angelico :
>>
>> If the first argument is None, the identity function is assumed. That
>> is, all elements of the iterable that are false are removed; it is
>> equivalent to (item for item in iterable if item). It is approximately
>> equivalent to (but faster than) filter(bool, iterable).
>>
>> ChrisA
>> --
>> https://mail.python.org/mailman/listinfo/python-list
>
>
> If you look in C source for `filter_next`
> https://github.com/python/cpython/blob/5d92647102fac9e116b98ab8bbc632eeed501c34/Python/bltinmodule.c#L593,
> there is a line:
>
> int checktrue = lz->func == Py_None || lz->func == (PyObject *)&PyBool_Type;
>
> So the only difference between `filter(None, ls`) and `filter(bool, ls)` is
> LOAD_NAME vs LOAD_CONST and that `None` is checked before than `bool`.
>

Assuming that nobody's shadowed the name 'bool' anywhere, which has to
be checked for at run time. (Which is the job of LOAD_NAME.)

ChrisA
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Kirill Balunov
2018-03-06 17:55 GMT+03:00 Chris Angelico :

> If the first argument is None, the identity function is assumed. That
> is, all elements of the iterable that are false are removed; it is
> equivalent to (item for item in iterable if item). It is approximately
> equivalent to (but faster than) filter(bool, iterable).
>
> ChrisA
> --
> https://mail.python.org/mailman/listinfo/python-list
>

If you look in C source for `filter_next`
https://github.com/python/cpython/blob/5d92647102fac9e116b98ab8bbc632eeed501c34/Python/bltinmodule.c#L593,
there is a line:

int checktrue = lz->func == Py_None || lz->func == (PyObject
*)&PyBool_Type;

So the only difference between `filter(None, ls`) and `filter(bool, ls)` is
LOAD_NAME vs LOAD_CONST and that `None` is checked before than `bool`.


With kind regards,
-gdg
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Chris Angelico
On Wed, Mar 7, 2018 at 2:12 AM, Kirill Balunov  wrote:
>
>
> 2018-03-06 17:55 GMT+03:00 Chris Angelico :
>>
>> On Wed, Mar 7, 2018 at 1:48 AM, Kirill Balunov 
>> wrote:
>> > Note: For some historical reasons as the first argument you can use None
>> > instead of function, in this case the identity function is assumed. That
>> > is, all elements of iterable that are false are removed which is
>> > equivalent
>> > to (item for item in iterable if item). Currently, for the same purpose
>> > the
>> > preferred form is `filter(bool, iterable)`.
>> >
>>
>> I'd prefer to word it something like:
>>
>> If the first argument is None, the identity function is assumed. That
>> is, all elements of the iterable that are false are removed; it is
>> equivalent to (item for item in iterable if item). It is approximately
>> equivalent to (but faster than) filter(bool, iterable).
>>
>> ChrisA
>> --
>> https://mail.python.org/mailman/listinfo/python-list
>
>
> I do not want to seem rude and stubborn, but how much faster is it to
> highlight or emphasize it:
>

Timings mean little. Why do we write:

if lst:

instead of:

if bool(lst):

? Because it's unnecessary and pointless to call bool() on something
before using it in a boolean context. If that concept causes you
problems, it's not the fault of the filter function; filter simply
uses something in a boolean context.

So "the identity function" is more correct than "the bool() function".

ChrisA
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Kirill Balunov
2018-03-06 17:55 GMT+03:00 Chris Angelico :

> On Wed, Mar 7, 2018 at 1:48 AM, Kirill Balunov 
> wrote:
> > Note: For some historical reasons as the first argument you can use None
> > instead of function, in this case the identity function is assumed. That
> > is, all elements of iterable that are false are removed which is
> equivalent
> > to (item for item in iterable if item). Currently, for the same purpose
> the
> > preferred form is `filter(bool, iterable)`.
> >
>
> I'd prefer to word it something like:
>
> If the first argument is None, the identity function is assumed. That
> is, all elements of the iterable that are false are removed; it is
> equivalent to (item for item in iterable if item). It is approximately
> equivalent to (but faster than) filter(bool, iterable).
>
> ChrisA
> --
> https://mail.python.org/mailman/listinfo/python-list
>

I do not want to seem rude and stubborn, but how much faster is it to
highlight or emphasize it:

from random import randint
for i in [1, 10, 100, 1000, 1, 10]:
ls = [randint(0,1) for _ in range(i)]
%timeit [*filter(None, ls)]
%timeit [*filter(bool, ls)]
print()

272 ns ± 0.0346 ns per loop (mean ± std. dev. of 7 runs, 100 loops each)
282 ns ± 0.0714 ns per loop (mean ± std. dev. of 7 runs, 100 loops each)

283 ns ± 0.0645 ns per loop (mean ± std. dev. of 7 runs, 100 loops each)
296 ns ± 0.116 ns per loop (mean ± std. dev. of 7 runs, 100 loops each)

1.4 µs ± 1.32 ns per loop (mean ± std. dev. of 7 runs, 100 loops each)
1.41 µs ± 4.05 ns per loop (mean ± std. dev. of 7 runs, 100 loops each)

14.7 µs ± 40.1 ns per loop (mean ± std. dev. of 7 runs, 10 loops each)
14.7 µs ± 23.2 ns per loop (mean ± std. dev. of 7 runs, 10 loops each)

137 µs ± 186 ns per loop (mean ± std. dev. of 7 runs, 1 loops each)
137 µs ± 24.7 ns per loop (mean ± std. dev. of 7 runs, 1 loops each)

1.32 ms ± 285 ns per loop (mean ± std. dev. of 7 runs, 1000 loops each)
1.32 ms ± 908 ns per loop (mean ± std. dev. of 7 runs, 1000 loops each)

With kind regards,
-gdg
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Chris Angelico
On Wed, Mar 7, 2018 at 1:48 AM, Kirill Balunov  wrote:
> Note: For some historical reasons as the first argument you can use None
> instead of function, in this case the identity function is assumed. That
> is, all elements of iterable that are false are removed which is equivalent
> to (item for item in iterable if item). Currently, for the same purpose the
> preferred form is `filter(bool, iterable)`.
>

I'd prefer to word it something like:

If the first argument is None, the identity function is assumed. That
is, all elements of the iterable that are false are removed; it is
equivalent to (item for item in iterable if item). It is approximately
equivalent to (but faster than) filter(bool, iterable).

ChrisA
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Kirill Balunov
2018-03-06 16:58 GMT+03:00 Jason Friedman :

>
> as a ordinary Python user I'd be interested in improvements to the
> documentation, including suggestions on real-world usage.
>

I'm just an ordinary user, just like you :)


> Kirill, taking deprecation/removal off the table, what changes would you
> recommend to the documentation?
>

My English is about basic level, so you may need to fix the spelling. But I
would write as follows:


filter(function, iterable)
Construct an iterator from those elements of iterable for which function
returns truthy values. iterable may be either a sequence, a container which
supports iteration, or an iterator.

Note that filter(function, iterable) is equivalent to the generator
expression (item for item in iterable if function(item)). In cases when
function corresponds to a simple lambda function a generator expression
should be preferred. For example, when it is necessary to eliminate all
multiples of three (x for x in range(100) if x % 3) should be used, instead
of filter(lambda x: x % 3, range(100))

See itertools.filterfalse() for the complementary function that returns
elements of iterable for which function returns false.

Note: For some historical reasons as the first argument you can use None
instead of function, in this case the identity function is assumed. That
is, all elements of iterable that are false are removed which is equivalent
to (item for item in iterable if item). Currently, for the same purpose the
preferred form is `filter(bool, iterable)`.

p.s.:
maybe _function_ should be changed to _callable_.

With kind regards,
-gdg
-- 
https://mail.python.org/mailman/listinfo/python-list


"except" and "subclasscheck" changed between CPython2 and 3

2018-03-06 Thread Youta TAKAOKA
Thank you, Steven.

> There is a feature-request to support that (as Python 2.7 does):
>
> https://bugs.python.org/issue12029
>
> but it is stalled.

I passed over the ticket.

Now, I know that this is a bug, but has not fixed yet.
There are (or ware ?) problems about performance and integrity for handling
exceptions.

It seems that a narrow range of use-cases cause the stalling.
Someday we have a type-focused VERY NICE library, (I hope that) it will be
resolved.

Thanks.

--
yout...@gmail.com
-- 
https://mail.python.org/mailman/listinfo/python-list


Layers of abstraction, was Re: RFC: Proposal: Deterministic Object Destruction

2018-03-06 Thread Peter Otten
Chris Angelico wrote:

> On Tue, Mar 6, 2018 at 10:04 AM, Steven D'Aprano
>  wrote:
>> # Later.
>> if __name__ = '__main__':
>> # Enter the Kingdom of Nouns.
> 
> Don't you need a NounKingdomEnterer to do that for you?

No, for some extra flexibility there should be a NounKingdomEntererFactory 
-- which of course has to implement the AbstractNounKingdomEntererFactory 
interface. Instantiating the right NounKingdomEntererFactory can easily be 
delegated to a NounKingdomEntererFactoryProducer. It's turtles^Wfactories 
all the way down...

I don't know how this will ever do anything -- my theory is that some good 
soul managed to sneak a few lines of javascript into the giant xml 
configuration file ;)
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Kirill Balunov
2018-03-06 16:35 GMT+03:00 Chris Green :

> It's 'deprecation', depreciation is something quite different.  People
> replying have spelt it correctly so you might possibly have noticed I
> thought/hoped.
>
> ... and it does matter a bit because it's not just a mis-spelling, the
> word you are using has its own meaning and could thus cause confusion.
>
> ... and, yes, I know it's a very common and easily made mistake. :-)
>
>
I did not ;) Thank you!

With kind regards,
-gdg
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Kirill Balunov
2018-03-06 16:51 GMT+03:00 Chris Angelico :

> On Wed, Mar 7, 2018 at 12:23 AM, Kirill Balunov 
> wrote:
> > Filter is generally faster than list comprehension or generators.
> >
> > %timeit [*filter(lambda x: x % 3, range(1000))]
> > 100 µs ± 16.4 ns per loop (mean ± std. dev. of 7 runs, 1 loops each)
> >
> > f = lambda x: x % 3
> >
> > %timeit [*(f(i) for i in range(1000))]
> > 132 µs ± 73.5 ns per loop (mean ± std. dev. of 7 runs, 1 loops each)
> >
> > %timeit [f(i) for i in range(1000)]
> > 107 µs ± 179 ns per loop (mean ± std. dev. of 7 runs, 1 loops each)
> >
>
> These don't do the same thing, though. A more comparable comprehension is:
>
> [i for i in range(1000) if i % 3]
>
> rosuav@sikorsky:~$ python3 -m timeit '[i for i in range(1000) if i % 3]'
> 1 loops, best of 5: 34.5 usec per loop
> rosuav@sikorsky:~$ python3 -m timeit '[*filter(lambda x: x % 3,
> range(1000))]'
> 5000 loops, best of 5: 81.1 usec per loop
>
> And my point about comprehensions was that you do NOT use a pointless
> function for them - you just have inline code. If there is a
> pre-existing function, sure! Use it. But when you use filter or map
> with a lambda function, you should probably use a comprehension
> instead.
>
> ChrisA
> --
> https://mail.python.org/mailman/listinfo/python-list
>

Thank you, I did not understand you at first, now everything is clear. In
this sense of `x % 3`, I fully agree with you.

With kind regards,
-gdg
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Jason Friedman
On Tue, Mar 6, 2018 at 1:52 AM, Kirill Balunov 
wrote:

>
> I propose to delete all references in the `filter` documentation that the
> first argument can be `None`, with possible depreciation of `None` as the
> the first argument - FutureWarning in Python 3.8+ and deleting this option
> in Python 4. Personally, regarding the last point - depreciation, I do not
> see this as a great necessity, but I do not find that the option with
> `None`
> should be offered and suggested through the documentation. Instead, it is
> better to show an example with using `filter(bool, iterable)` which is
> absolutely
> equivalent, more readable, but a little bit slower.
>
> Currently documentation for `None` case uses `identity function is
> assumed`, what is this `identity` and how it is consistent with
> truthfulness?
>
> In addition, this change makes the perception of `map` and `filter` more
> consistent,with the rule that first argument must be `callable`.
>
> I see only one moment with `None`, since `None` is a keyword, the behavior
> of `filter(None, iterable)` is alsways guaranteed, but with `bool` it is
> not. Nevertheless, we are all adults here.
>

I won't pretend I am qualified to debate the technical aspects here, but
regarding this snippet:

... Instead, it is better to show an example with using `filter(bool,
iterable)` which is absolutely equivalent, more readable ...

as a ordinary Python user I'd be interested in improvements to the
documentation, including suggestions on real-world usage.  For example,
Chris Angelico below says in part:

... that said, though, any use of filter() that involves a lambda
function should
probably become list comps or genexps, so filter itself should only be used
when ...

Kirill, taking deprecation/removal off the table, what changes would you
recommend to the documentation?
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Chris Angelico
On Wed, Mar 7, 2018 at 12:23 AM, Kirill Balunov  wrote:
> Filter is generally faster than list comprehension or generators.
>
> %timeit [*filter(lambda x: x % 3, range(1000))]
> 100 µs ± 16.4 ns per loop (mean ± std. dev. of 7 runs, 1 loops each)
>
> f = lambda x: x % 3
>
> %timeit [*(f(i) for i in range(1000))]
> 132 µs ± 73.5 ns per loop (mean ± std. dev. of 7 runs, 1 loops each)
>
> %timeit [f(i) for i in range(1000)]
> 107 µs ± 179 ns per loop (mean ± std. dev. of 7 runs, 1 loops each)
>

These don't do the same thing, though. A more comparable comprehension is:

[i for i in range(1000) if i % 3]

rosuav@sikorsky:~$ python3 -m timeit '[i for i in range(1000) if i % 3]'
1 loops, best of 5: 34.5 usec per loop
rosuav@sikorsky:~$ python3 -m timeit '[*filter(lambda x: x % 3, range(1000))]'
5000 loops, best of 5: 81.1 usec per loop

And my point about comprehensions was that you do NOT use a pointless
function for them - you just have inline code. If there is a
pre-existing function, sure! Use it. But when you use filter or map
with a lambda function, you should probably use a comprehension
instead.

ChrisA
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Chris Green
Kirill Balunov  wrote:
> 
> As I wrote, __possible depreciation__, I also do not see the point of just

It's 'deprecation', depreciation is something quite different.  People
replying have spelt it correctly so you might possibly have noticed I
thought/hoped.

... and it does matter a bit because it's not just a mis-spelling, the
word you are using has its own meaning and could thus cause confusion.

... and, yes, I know it's a very common and easily made mistake. :-)

-- 
Chris Green
·
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Kirill Balunov
2018-03-06 13:18 GMT+03:00 Chris Angelico :

> The identity function is:
>
> filter(lambda x: x, range(10))
>
> How is it consistent with truthiness? Exactly the same way the
> underlying object is. There's no requirement for the predicate
> function to return True or False - it's perfectly acceptable, for
> instance, to do this:
>
> filter(lambda x: x % 3, range(10))
>
> to eliminate all multiples of three.
>

Yes there is no reason to return True and False, but in the case of `None`
and `bool` under the hood there will be no difference and the form with
`bool` is much more readable.


>
> That said, though, any use of filter() that involves a lambda function
> should probably become list comps or genexps, so filter itself should
> only be used when there really IS a pre-existing function that does
> the job.


Filter is generally faster than list comprehension or generators.

%timeit [*filter(lambda x: x % 3, range(1000))]
100 µs ± 16.4 ns per loop (mean ± std. dev. of 7 runs, 1 loops each)

f = lambda x: x % 3

%timeit [*(f(i) for i in range(1000))]
132 µs ± 73.5 ns per loop (mean ± std. dev. of 7 runs, 1 loops each)

%timeit [f(i) for i in range(1000)]
107 µs ± 179 ns per loop (mean ± std. dev. of 7 runs, 1 loops each)


> So, for instance, you could strip out every occurrence of the
> string "0" with:
>
> filter(int, list_of_strings)
>
> And that still depends on the normal Python rules for boolification.
> If that's valid, then it should be just as viable to say
> "filter(identity-function, ...)", which is spelled "filter(None,
> ...)".
>
> ChrisA
> --
> https://mail.python.org/mailman/listinfo/python-list
>
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Kirill Balunov
2018-03-06 14:17 GMT+03:00 Steven D'Aprano <
steve+comp.lang.pyt...@pearwood.info>:

> On Tue, 06 Mar 2018 11:52:22 +0300, Kirill Balunov wrote:
>
> > I propose to delete all references in the `filter` documentation that
> > the first argument can be `None`, with possible depreciation of `None`
> > as the the first argument - FutureWarning in Python 3.8+ and deleting
> > this option in Python 4.
>
> Even if we agreed that it is unfortunate that filter accepts None as an
> argument, since it does (and has done since Python 1.0) there is nothing
> to be gained by deprecating and removing it.
>
> Deprecating and removing it will break code that currently works, for no
> good reason; removing the documentation is unacceptable, as that makes it
> too difficult for people to find out what `filter(None, values)` does.
>

As I wrote, __possible depreciation__, I also do not see the point of just
breaking someone's code. But I didn't see any benefit to explicitly promote
`filter(None, iterable)` form in the documentation as a good style.


> > Instead, it is better to show an example with using
> > `filter(bool, iterable)` which is absolutely
> > equivalent, more readable, but a little bit slower.
>
> So long as `filter(None, ...)` is still documented, I don't mind what
> example is given.
>
> But the idiom `filter(None, ...)` is an old, common idiom, very familiar
> to many people who have a background in functional programming.
>

While this form familiar and common idiom for those who are familiar with
Python from versions < 2.3, before `bool` type was introduced. It looks
kinky for newcomers and not obvious at a glance. In functional programming
we use a predicate, and `None` does not match predicate definition, while
`bool` does!


> It is unfortunate that filter takes the arguments in the order it does.
> Perhaps it would have been better to write it like this:
>
> def filter(iterable, predicate=None):
> ...
>
>
> Then `filter(values, None)` would be a standard Python idiom, explicitly
> saying to use the default predicate function. There is no difference to
> `filter(None, values)` except the order is (sadly) reversed.
>

If such a form was in Python, I probably would agree with you. Although in
its present form I like it a lot more and find it more intuitive.

> Currently documentation for `None` case uses `identity function is
> > assumed`, what is this `identity` and how it is consistent with
> > truthfulness?
>
> The identity function is a mathematical term for a function that returns
> its argument unchanged:
>
> def identity(x):
> return x
>
> So `filter(func, values)` filters according to func(x); using None
> instead filters according to x alone, without the expense of calling a do-
> nothing function:
>
> # slow because it has to call the lambda function each time;
> filter(lambda x: x, values)
>
> # fast because filter takes an optimized path
> filter(None, values)
>


> Since filter filters according to the truthy or falsey value of x, it
> isn't actually necessary to call bool(x). In Python, all values are
> automatically considered either truthy or falsey. The reason to call
> bool() is to ensure you have a canonical True/False value, and there's no
> need for that here.


I went over a bit with the question what is identity function :) But I have
a feeling that I perceive all of the above quite the contrary in the
context of a `filter` function. And since filter filters according to the
truthy or falsey value of x. `None` and `bool` should behave totally
equivalent under the hood and I'm 99% sure that it is so.


> So the identity function should be preferred to bool,
> for those who understand two things:
>
> - the identity function (using None as the predicate function)
>   returns x unchanged;
>

Sorry, but how does the above relates to the `filter` discussion?


>
> - and that x, like all values, automatically has a truthy value in a
>   boolean context (which includes filter).
>
>
Yes, and that is why there is no point to `None` since they will do the
same thing in context of `filter` function.


> > In addition, this change makes the perception of `map` and `filter` more
> > consistent,with the rule that first argument must be `callable`.
>
> I consider that a flaw in map. map should also accept None as the
> identity function, so that map(None, iterable) returns the values of
> iterable unchanged.
>
> def map(function=None, *iterables):
> if len(iterables) == 0:
> raise TypeError("map() must have at least two arguments.")
> if function is None:
> if len(iterables) > 1:
> return zip(*iterables)
> else:
> assert len(iterables) == 1
> return iter(iterables[0])
> elif len(iterables) > 1:
> return (function(*args) for args in zip(*iterables))
> else:
> assert len(iterables) == 1
> return (function(arg) for arg in iterables[0])
>

And what will be the practical reason to have this? :)

W

Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Steven D'Aprano
On Tue, 06 Mar 2018 11:52:22 +0300, Kirill Balunov wrote:

> I propose to delete all references in the `filter` documentation that
> the first argument can be `None`, with possible depreciation of `None`
> as the the first argument - FutureWarning in Python 3.8+ and deleting
> this option in Python 4.

Even if we agreed that it is unfortunate that filter accepts None as an 
argument, since it does (and has done since Python 1.0) there is nothing 
to be gained by deprecating and removing it.

Deprecating and removing it will break code that currently works, for no 
good reason; removing the documentation is unacceptable, as that makes it 
too difficult for people to find out what `filter(None, values)` does.


> Instead, it is better to show an example with using
> `filter(bool, iterable)` which is absolutely
> equivalent, more readable, but a little bit slower.

So long as `filter(None, ...)` is still documented, I don't mind what 
example is given.

But the idiom `filter(None, ...)` is an old, common idiom, very familiar 
to many people who have a background in functional programming.

It is unfortunate that filter takes the arguments in the order it does. 
Perhaps it would have been better to write it like this:

def filter(iterable, predicate=None):
...


Then `filter(values, None)` would be a standard Python idiom, explicitly 
saying to use the default predicate function. There is no difference to 
`filter(None, values)` except the order is (sadly) reversed.


> Currently documentation for `None` case uses `identity function is
> assumed`, what is this `identity` and how it is consistent with
> truthfulness?

The identity function is a mathematical term for a function that returns 
its argument unchanged:

def identity(x):
return x

So `filter(func, values)` filters according to func(x); using None 
instead filters according to x alone, without the expense of calling a do-
nothing function:

# slow because it has to call the lambda function each time;
filter(lambda x: x, values)

# fast because filter takes an optimized path
filter(None, values)


Since filter filters according to the truthy or falsey value of x, it 
isn't actually necessary to call bool(x). In Python, all values are 
automatically considered either truthy or falsey. The reason to call 
bool() is to ensure you have a canonical True/False value, and there's no 
need for that here. So the identity function should be preferred to bool, 
for those who understand two things:

- the identity function (using None as the predicate function) 
  returns x unchanged;

- and that x, like all values, automatically has a truthy value in a
  boolean context (which includes filter).


> In addition, this change makes the perception of `map` and `filter` more
> consistent,with the rule that first argument must be `callable`.

I consider that a flaw in map. map should also accept None as the 
identity function, so that map(None, iterable) returns the values of 
iterable unchanged.

def map(function=None, *iterables):
if len(iterables) == 0:
raise TypeError("map() must have at least two arguments.")
if function is None:
if len(iterables) > 1:
return zip(*iterables)
else:
assert len(iterables) == 1
return iter(iterables[0])
elif len(iterables) > 1:
return (function(*args) for args in zip(*iterables))
else:
assert len(iterables) == 1
return (function(arg) for arg in iterables[0])


-- 
Steve

-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Bitstream -- Binary Data for Humans (Posting On Python-List Prohibited)

2018-03-06 Thread Sébastien Boisgérault
Le mardi 6 mars 2018 11:15:15 UTC+1, Terry Reedy a écrit :
> On 3/6/2018 3:58 AM, Sébastien Boisgérault wrote:
> > Hi Lawrence,
> > 
> > Le mardi 6 mars 2018 01:20:36 UTC+1, Lawrence D’Oliveiro a écrit :
> >> On Tuesday, March 6, 2018 at 8:06:00 AM UTC+13, Sébastien Boisgérault 
> >> wrote:
> >>> I have released bitstream, a Python library to manage binary data
> >>> (at the byte or bit level), hopefully without the pain that this kind
> >>> of thing usually entails :)
> >>
> >>> byte_index = offset / 8
> >>
> >> This will return a float.
> 
> byte_index // 8
> will give you the int index directly in both late 2.x and 3.x.

Indeed! And since this is Cython code, I *guess* that I should combine `//` 
with the 'cdivision' set to True to get the syntax that everyone understands 
*and* the pure C speed (see 
http://cython.readthedocs.io/en/latest/src/reference/compilation.html). I need 
to run some experiments to make sure that this behaves as expected, but this is 
very likely the way to go.



> -- 
> Terry Jan Redey

-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Chris Angelico
On Tue, Mar 6, 2018 at 7:52 PM, Kirill Balunov  wrote:
> This thought occurred to me several times, but I could not decide to write.
> And since `filter` is a builtin, I think this change should be discussed
> here, before opening an issue on bug tracker.
>
> I propose to delete all references in the `filter` documentation that the
> first argument can be `None`, with possible depreciation of `None` as the
> the first argument - FutureWarning in Python 3.8+ and deleting this option
> in Python 4. Personally, regarding the last point - depreciation, I do not
> see this as a great necessity, but I do not find that the option with `None`
> should be offered and suggested through the documentation. Instead, it is
> better to show an example with using `filter(bool, iterable)` which is
> absolutely
> equivalent, more readable, but a little bit slower.
>
> %timeit [*filter(None, range(10))]
> 503 ns ± 0.259 ns per loop (mean ± std. dev. of 7 runs, 100 loops each)
>
> %timeit [*filter(bool, range(10))]
> 512 ns ± 1.09 ns per loop (mean ± std. dev. of 7 runs, 100 loops each)
>
> Currently documentation for `None` case uses `identity function is
> assumed`, what is this `identity` and how it is consistent with
> truthfulness?

The identity function is:

filter(lambda x: x, range(10))

How is it consistent with truthiness? Exactly the same way the
underlying object is. There's no requirement for the predicate
function to return True or False - it's perfectly acceptable, for
instance, to do this:

filter(lambda x: x % 3, range(10))

to eliminate all multiples of three.

That said, though, any use of filter() that involves a lambda function
should probably become list comps or genexps, so filter itself should
only be used when there really IS a pre-existing function that does
the job. So, for instance, you could strip out every occurrence of the
string "0" with:

filter(int, list_of_strings)

And that still depends on the normal Python rules for boolification.
If that's valid, then it should be just as viable to say
"filter(identity-function, ...)", which is spelled "filter(None,
...)".

ChrisA
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Bitstream -- Binary Data for Humans (Posting On Python-List Prohibited)

2018-03-06 Thread Terry Reedy

On 3/6/2018 3:58 AM, Sébastien Boisgérault wrote:

Hi Lawrence,

Le mardi 6 mars 2018 01:20:36 UTC+1, Lawrence D’Oliveiro a écrit :

On Tuesday, March 6, 2018 at 8:06:00 AM UTC+13, Sébastien Boisgérault wrote:

I have released bitstream, a Python library to manage binary data
(at the byte or bit level), hopefully without the pain that this kind
of thing usually entails :)



byte_index = offset / 8


This will return a float.


byte_index // 8
will give you the int index directly in both late 2.x and 3.x.

--
Terry Jan Redey


--
https://mail.python.org/mailman/listinfo/python-list


Re: Ways to make a free variable local to a function?

2018-03-06 Thread Chris Angelico
On Tue, Mar 6, 2018 at 8:02 PM, Kirill Balunov  wrote:
>
>
> 2018-03-05 17:34 GMT+03:00 Chris Angelico :
>>
>> In theory, the CPython bytecode compiler (don't know about other
>> Python implementations) could just add these as constants. They'd then
>> be bound at either compile time or function definition time (by
>> default the former, I think, but the latter would be more useful), and
>> be looked up as quickly as locals. I'm not sure how useful this would
>> be, though.
>
>
> With some assumptions, It will be useful for every function call:-)
>
>> If PEP 572 [1] were to be accepted, you could do something like this:
>>
>> def func(numb):
>> if ((int as int), (float as float)):
>> res = []
>> for i in range(numb):
>> res.append(int(i) + float(i))
>> return res
>>
>> Syntactically a bit clunky, but keeps everything inside the function,
>> and DOES create local variables. Not sure it's better than your other
>> options, but it is another option.
>
>
> While I'm +0.5 on yours PEP 572 idea, especially in `while` and `if`
> statements, this example is an overuse of the proposed syntax ;-) Also it
> will add an overhead on every function call, and as you said  -
> "Syntactically a bit clunky".
>

The run-time overhead should be insignificant; this kind of
optimization is done when you're running a tight loop, so it's the run
time of the loop body that dominates the function. That's also why I
do NOT want this to happen at compile time, even though that would be
the easiest. The very latest this should happen is function definition
time; it would be extremely surprising otherwise. And if it happens
once when the function's called, that's usually not going to be much
cost compared to the saving of LOAD_FAST instead of LOAD_GLOBAL in
each iteration of the loop.

ChrisA
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Ways to make a free variable local to a function?

2018-03-06 Thread Kirill Balunov
 2018-03-05 21:44 GMT+03:00 Terry Reedy :

> Yes, what we really want for this sort of thing are unrebindable local
> constants.  A simple syntax change could do it.
>
>  def func_local_1(numb; int = int, float = float, range = range):
>
> The binding after ';' belong in the header because they should be done
> once.
>
> They'd then
>> be bound at either compile time or function definition time (by
>> default the former, I think, but the latter would be more useful), and
>> be looked up as quickly as locals. I'm not sure how useful this would
>> be, though.
>>
>
> I believe that the occasional practice of re-binding built-in names to
> locals can be shown to speed up loops run enough times.


Yes "_unrebindable local constants_" it is what I was thinking about. But I
do not agree that they must be passed through arguments, because they
should be somewhat static for a function, and could not be changed by any
means after function is compiled.
Alternative option, more dynamic - to allow injecting local variables into
the function via some interface. Currently, there is no such _feature_ in
Python, at least I do not know. There was _somewhat_ related discussion
about how to change the locals of a frame (https://bugs.python.org/
issue1654367) by making `frame.f_locals` writable, but it seems that it is
dead.

With kind regards,
-gdg
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Bitstream -- Binary Data for Humans (Posting On Python-List Prohibited)

2018-03-06 Thread Sébastien Boisgérault
Le mardi 6 mars 2018 10:23:02 UTC+1, Lawrence D’Oliveiro a écrit :
> On Tuesday, March 6, 2018 at 9:59:55 PM UTC+13, Sébastien Boisgérault wrote:
> > 
> > Le mardi 6 mars 2018 01:20:36 UTC+1, Lawrence D’Oliveiro a écrit :
> >
> >> On Tuesday, March 6, 2018 at 8:06:00 AM UTC+13, Sébastien Boisgérault 
> >> wrote:
> >>>
> >>>byte_index = offset / 8
> >> 
> >> This will return a float.
> > 
> > The implementation is in Cython, which allows to declare types. 
> > The variable byte_index is defined as a size_t. 
> 
> Ah, I see. Still it seems unPythonic to use ”/” for integer division. Does it 
> not allow “//”?

Yes, '//' works, see:


https://mybinder.org/v2/gh/boisgera/jupyter-cython/master?filepath=Integer%20Division.ipynb

Actually, in this Jupyter notebook setting, this is '/' that doesn't work!
I should have a new look at this; since performance also matters,
I'd also like to have the Cython code with the smallest overhead 
(even if it is less readable/Pythonic).

Cheers,

SB
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Ways to make a free variable local to a function?

2018-03-06 Thread Wolfgang Maier

On 03/05/2018 07:44 PM, Terry Reedy wrote:

On 3/5/2018 9:34 AM, Chris Angelico wrote:

On Tue, Mar 6, 2018 at 12:52 AM, Terry Reedy  wrote:

On 3/5/2018 7:12 AM, Kirill Balunov wrote:

# 1. By passing through local variable's default values

   def func_local_1(numb, _int = int, _float = float, _range = range):



You are not required to mangle the names.

def func_local_1(numb, int = int, float = float, range = range):
...



Even so, this does mess up the function's signature,


Which I why I only said that using the original names solves the syntax
highlighting issue (of marking built-ins as built-ins).


leaving your
callers wondering if they can call it with some sort of range
parameter. (Though in this particular instance, range() is only called
once, so it's pretty much useless to try to optimize it.)

In theory, the CPython bytecode compiler (don't know about other
Python implementations) could just add these as constants.


Yes, what we really want for this sort of thing are unrebindable local
constants.  A simple syntax change could do it.

   def func_local_1(numb; int = int, float = float, range = range):

The binding after ';' belong in the header because they should be done once.



Ah, I did not really understand initially what Kirill was trying to 
achieve by putting the name binding into the function signature.
Now I do, but I don't think it is a good idea. Sanctioning this with 
dedicated syntax would only make Python more static because for any 
function defined this way, you would lose the ability to alter the 
behavior of that function through changing the global binding after the 
function has been called (in the example above, you could no longer mock 
replace int, float and range on subsequent func_local_1 calls) and I 
don't think this is something that should be encouraged.


Wolfgang


--
https://mail.python.org/mailman/listinfo/python-list


Re: Bitstream -- Binary Data for Humans

2018-03-06 Thread Sébastien Boisgérault
Le mardi 6 mars 2018 09:26:50 UTC+1, Sébastien Boisgérault a écrit :
> Le mardi 6 mars 2018 00:29:25 UTC+1, Roel Schroeven a écrit :
> > Sébastien Boisgérault schreef op 5/03/2018 20:05:
> > > I have released bitstream, a Python library to manage binary data (at the 
> > > byte or bit level),
> >  > hopefully without the pain that this kind of thing usually entails :)
> > > 
> > > If you have struggled with this topic in the past, please take a look at 
> > > the documentation
> >  > (http://boisgera.github.io/bitstream/) and tell me what you think.
> > 
> > Hi Sébastien,
> > 
> > At work I have some Python code to decode AIS[1] messages, for which I 
> > created my own code for handling binary data. It works, but is pretty 
> > slow. Not surprising, since handling data at the bit level is not 
> > exactly Python's strength. If I find the time, I'll try to replace my 
> > code with your bitstream and see if it does what I need it to do, and if 
> > it's any faster.
> > 
> > If/when I actually get around to it, I'll keep you informed.
> > 
> > [1] https://en.wikipedia.org/wiki/Automatic_identification_system
> > 
> > 
> > Best regards,
> > Roel
> > 
> > -- 
> > The saddest aspect of life right now is that science gathers knowledge
> > faster than society gathers wisdom.
> >-- Isaac Asimov
> > 
> > Roel Schroeven
> 
> Great, thanks !

Hi again Roel,

I had a look at the AIS message format from your link 
(https://en.wikipedia.org/wiki/Automatic_identification_system#Message_format) 
and this seems to be a nice use case; all the data components seem to be nicely 
aligned on the byte boundary ... until you see that the payload uses ASCII6(*), 
which I didn't know about. 

Thanks again for the info!

Cheers,

(*) ASCII6 code = ASCII code + 48; 
(http://catb.org/gpsd/AIVDM.html#_aivdm_aivdo_sentence_layer)
SB



-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Ways to make a free variable local to a function?

2018-03-06 Thread Kirill Balunov
2018-03-05 17:34 GMT+03:00 Chris Angelico :

> In theory, the CPython bytecode compiler (don't know about other
> Python implementations) could just add these as constants. They'd then
> be bound at either compile time or function definition time (by
> default the former, I think, but the latter would be more useful), and
> be looked up as quickly as locals. I'm not sure how useful this would
> be, though.
>

With some assumptions, It will be useful for every function call:-)

If PEP 572 [1] were to be accepted, you could do something like this:
>
> def func(numb):
> if ((int as int), (float as float)):
> res = []
> for i in range(numb):
> res.append(int(i) + float(i))
> return res
>
> Syntactically a bit clunky, but keeps everything inside the function,
> and DOES create local variables. Not sure it's better than your other
> options, but it is another option.
>

While I'm +0.5 on yours PEP 572 idea, especially in `while` and `if`
statements, this example is an overuse of the proposed syntax ;-) Also it
will add an overhead on every function call, and as you said  -
"Syntactically a bit clunky".

With kind regards,
-gdg
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Bitstream -- Binary Data for Humans (Posting On Python-List Prohibited)

2018-03-06 Thread Sébastien Boisgérault
Hi Lawrence,

Le mardi 6 mars 2018 01:20:36 UTC+1, Lawrence D’Oliveiro a écrit :
> On Tuesday, March 6, 2018 at 8:06:00 AM UTC+13, Sébastien Boisgérault wrote:
> > I have released bitstream, a Python library to manage binary data
> > (at the byte or bit level), hopefully without the pain that this kind
> > of thing usually entails :)
> 
> >byte_index = offset / 8
> 
> This will return a float.

The implementation is in Cython, which allows to declare types. 
The variable byte_index is defined as a size_t. 
Did I miss something? Do you mean that an intermediate float 
is used in the generated C code? I guess I should check that.
I realize now that I sometimes use the code above to get the bit
and bytes index and sometimes divmod ...

> 
> Also I notice you count bit positions from the top of each byte, rather than 
> from the bottom. Any reason for this?

I suppose that my mental representation of the bitstream is left-to-right 
(think sequence of bits) with bits being "big-endian"ish in each byte, 
therefore new bits enter from the left with big weights. Which should translate 
to your description. So, no, no specific reason for this I guess. Is one of the 
representation better that the other (wrt performance for example)?.

Cheers,

SB

-- 
https://mail.python.org/mailman/listinfo/python-list


Do not promote `None` as the first argument to `filter` in documentation.

2018-03-06 Thread Kirill Balunov
This thought occurred to me several times, but I could not decide to write.
And since `filter` is a builtin, I think this change should be discussed
here, before opening an issue on bug tracker.

I propose to delete all references in the `filter` documentation that the
first argument can be `None`, with possible depreciation of `None` as the
the first argument - FutureWarning in Python 3.8+ and deleting this option
in Python 4. Personally, regarding the last point - depreciation, I do not
see this as a great necessity, but I do not find that the option with `None`
should be offered and suggested through the documentation. Instead, it is
better to show an example with using `filter(bool, iterable)` which is
absolutely
equivalent, more readable, but a little bit slower.

%timeit [*filter(None, range(10))]
503 ns ± 0.259 ns per loop (mean ± std. dev. of 7 runs, 100 loops each)

%timeit [*filter(bool, range(10))]
512 ns ± 1.09 ns per loop (mean ± std. dev. of 7 runs, 100 loops each)

Currently documentation for `None` case uses `identity function is
assumed`, what is this `identity` and how it is consistent with
truthfulness?

In addition, this change makes the perception of `map` and `filter` more
consistent,with the rule that first argument must be `callable`.

I see only one moment with `None`, since `None` is a keyword, the behavior
of `filter(None, iterable)` is alsways guaranteed, but with `bool` it is
not. Nevertheless, we are all adults here.

With kind regards,
-gdg
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Bitstream -- Binary Data for Humans

2018-03-06 Thread Sébastien Boisgérault
Le mardi 6 mars 2018 00:29:25 UTC+1, Roel Schroeven a écrit :
> Sébastien Boisgérault schreef op 5/03/2018 20:05:
> > I have released bitstream, a Python library to manage binary data (at the 
> > byte or bit level),
>  > hopefully without the pain that this kind of thing usually entails :)
> > 
> > If you have struggled with this topic in the past, please take a look at 
> > the documentation
>  > (http://boisgera.github.io/bitstream/) and tell me what you think.
> 
> Hi Sébastien,
> 
> At work I have some Python code to decode AIS[1] messages, for which I 
> created my own code for handling binary data. It works, but is pretty 
> slow. Not surprising, since handling data at the bit level is not 
> exactly Python's strength. If I find the time, I'll try to replace my 
> code with your bitstream and see if it does what I need it to do, and if 
> it's any faster.
> 
> If/when I actually get around to it, I'll keep you informed.
> 
> [1] https://en.wikipedia.org/wiki/Automatic_identification_system
> 
> 
> Best regards,
> Roel
> 
> -- 
> The saddest aspect of life right now is that science gathers knowledge
> faster than society gathers wisdom.
>-- Isaac Asimov
> 
> Roel Schroeven

Great, thanks !
-- 
https://mail.python.org/mailman/listinfo/python-list