Re: Holding until next value change

2016-08-20 Thread Arshpreet Singh
On Saturday, 20 August 2016 11:38:03 UTC+5:30, Steve D'Aprano  wrote:
> On Sat, 20 Aug 2016 02:53 pm, Arshpreet Singh wrote:
> 
> > I am writing a function as main_call() which is continuously producing
> > values. (+ve or -ve) I want to print on screen only for first +ve value
> > and hold until -ve value comes around. here is my code:
> > 
> > 
> > def main_call():
> > while True:
> > yield strategy()
> >  
> > for value in main_call():
> > if(value>0):
> > print '+ve'
> > elif(value>0):
> > print '-ve'
> > else:
> > pass
> > 
> > Do I need to use threads or processes?
> 
> Only if you want a major headache.
> 
> 
> Your code doesn't do what you want it to do. It prints "+ve" every time it
> sees a positive value, not just the first time.
> 
> One solution to this is to think of a state machine: your machine starts off
> in the state:
> 
> (1) Ignore negative values, print the first positive value you see, 
> then change to the next state.
> 
> The second state is:
> 
> (2) Ignore positive values, print the first negative value you see,
> then change to the next state.
> 
> The third state is unspecified. You don't know say what it is, so I'm going
> to guess that you change to a third state:
> 
> (3) Don't ignore anything, print every value you see.
> 
> 
> So here are our three machines:
> 
> def ignore_negative(x):
> if x < 0:
> return False
> else:
> print("+ve")
> return True
> 
> def ignore_positive(x):
> if x > 0:
> return False
> else:
> print("-ve")
> return True
> 
> def ignore_nothing(x):
> if x > 0:
> print("+ve")
> else:
> print("-ve")
> return False
> 
> 
> Here is a table that specifies the changes in state:
> 
> TABLE = { # current state: next state
> ignore_negative: ignore_positive,
> ignore_positive: ignore_nothing,
> }
> 
> 
> And some code to drive it:
> 
> 
> state = ignore_negative  # DON'T call the function yet
> for value in main_call():
> print(value)  # for testing
> if state(value):
> print("changing state")
> state = TABLE[state]
Hi Steve, my third state is if x==0 , I tired the same code but here is output 
I am getting, so we are changing the state even it is printing out the +ve as 
well as -ve values

8.7664352813e-05
+ve
changing state
8.7664352813e-05
8.7664352813e-05
8.7664352813e-05
8.7664352813e-05
8.7664352813e-05
8.76628243948e-05
8.30490294982e-05
8.30490294982e-05
6.45892873188e-05
6.45892873188e-05
6.45892873188e-05
6.45892873188e-05
-4.61232547941e-06
-ve
changing state
-4.61232547941e-06
-ve
-4.61232547941e-06
-ve
-4.61232547941e-06
-ve
-4.61232547941e-06
-ve
-4.61232547941e-06
-ve
-4.61232547941e-06
-ve
-4.61232547941e-06
-ve
-4.61232547941e-06
-ve
-4.61232547941e-06
-ve
-4.61232547941e-06
-ve
-4.61232547941e-06
-ve
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: saving octet-stream png file

2016-08-20 Thread Marko Rauhamaa

Random832 :
> On Fri, Aug 19, 2016, at 16:51, Lawrence D’Oliveiro wrote:
>> On Saturday, August 20, 2016 at 6:03:53 AM UTC+12, Terry Reedy wrote:
>> > An 'octet' is a byte of 8 bits.
>> Is there any other size of byte?
> Not very often anymore.

The main difference between an octet and a byte is that a "byte" is used
when talking about computers while an "octet" is a term used in
telecommunications protocols.

(If I'm not mistaken, "octet" is also French for "byte".)

Somewhat analogously, a programmer can rely on integers being
2's-complement. IOW, even in Python,

-X == ~X + 1

for any integer.

2'scomplement arithmetics is quite often taken advantage of in C
programming. Unfortunately, with the castration of signed integers with
the most recent C standards, 2's-complement has been dangerously broken.


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


Re: The Joys Of Data-Driven Programming

2016-08-20 Thread Marko Rauhamaa
Lawrence D’Oliveiro :

> On Thursday, August 18, 2016 at 4:47:28 PM UTC+12, Marko Rauhamaa wrote:
>> ... as a rule, I dislike rules. Rule languages tend to
>> grow out of all bounds, always remain deficient and have impenetrable,
>> ad-hoc semantics.
>
> That’s a very peculiar thing to say, considering that data-driven
> programming is a well-known technique for writing compact code.
>
> Less code, and in particular, less repetitive code => fewer bugs.

I can't relate to what you say.

All I can say is that I've encountered numerous bad cases of rule
systems, eg:

 - iptables

 - selinux policies

 - systemd unit files

 - asterisk

 - sendmail


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


Re: use regex to search the page one time to get two types of Information

2016-08-20 Thread iMath
On Friday, August 19, 2016 at 9:19:22 PM UTC+8, Chris Angelico wrote:
> On Fri, Aug 19, 2016 at 11:13 PM, iMath  wrote:
> > 1. searching the page two times rather than one is a little bit time 
> > consuming .
> 
> Have you measured that? If not, ignore it. You're searching a web
> page; if you're downloading that before you search it, chances are
> very good that you spend far more time waiting for the download than
> you ever will on the regex.
> 
> ChrisA

tested,  searching the page two times rather than one is a little bit time 
consuming . 
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: use regex to search the page one time to get two types of Information

2016-08-20 Thread iMath
On Friday, August 19, 2016 at 9:45:08 PM UTC+8, Friedrich Rentsch wrote:
> On 08/19/2016 09:02 AM, iMath wrote:
> > I need to use regex to search two types of Information within a web page, 
> > while it seems  searching the page two times rather than one is much time 
> > consuming , is it possible to search the page one time to get two or more 
> > types of Information?
> 
>  >>> r = re.compile ('page|Information|time')
>  >>> r.findall ( (your post) )
> ['Information', 'page', 'page', 'time', 'time', 'page', 'time', 
> 'Information']
> 
> Does that look right?
> 
> Frederic

I found starting the second search from the first match.endpos does reduce the 
time consuming, with less time consuming than your solution ,thanks anyway !
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: index for regex.search() beyond which the RE engine will not go.

2016-08-20 Thread iMath
On Friday, August 19, 2016 at 10:09:19 PM UTC+8, Steve D'Aprano wrote:
> On Fri, 19 Aug 2016 09:14 pm, iMath wrote:
> 
> > 
> > for
> > regex.search(string[, pos[, endpos]])
> > The optional parameter endpos is the index into the string beyond which
> > the RE engine will not go, while this lead me to believe the RE engine
> > will still search on till the endpos position even after it returned the
> > matched object, is this Right ?
> 
> No.
> 
> Once the RE engine finds a match, it stops. You can test this for yourself
> with a small timing test, using the "timeit" module.
> 
> from timeit import Timer
> huge_string = 'aaabc' + 'a'*100 + 'dea'
> re1 = r'ab.a'
> re2 = r'ad.a'
> 
> # set up some code to time.
> setup = 'import re; from __main__ import huge_string, re1, re2'
> t1 = Timer('re.search(re1, huge_string)', setup)
> t2 = Timer('re.search(re2, huge_string)', setup)
> 
> # Now run the timers.
> best = min(t1.repeat(number=1000))/1000
> print("Time to locate regex at the start of huge string:", best)
> best = min(t2.repeat(number=1000))/1000
> print("Time to locate regex at the end of the huge string:", best)
> 
> 
> 
> When I run that on my computer, it prints:
> 
> Time to locate regex at the start of huge string: 4.9710273742675785e-06
> Time to locate regex at the end of the huge string: 0.0038938069343566893
> 
> 
> So it takes about 4.9 microseconds to find the regex at the beginning of the
> string. To find the regex at the end of the string takes about 3893
> microseconds.
> 
> 
> The "endpos" parameter tells the RE engine to stop at that position if the
> regex isn't found before it. It won't go beyond that point.
> 
> 
> 
> 
> 
> 
> -- 
> Steve
> “Cheer up,” they said, “things could be worse.” So I cheered up, and sure
> enough, things got worse.

Thanks for clarifying
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Michael Selik
On Fri, Aug 19, 2016 at 5:01 AM Lawrence D’Oliveiro 
wrote:

> It is handy to be able to keep complex expressions together sometimes,
> when breaking them up would simply obscure their structure. To avoid lines
> getting long, why not take advantage of the two available screen/page
> dimensions to make their structure clearer? As a bonus, spacing out
> parentheses makes them look less of a clutter.
>
>

> Examples from <
> https://github.com/ldo/qahirah_examples/blob/master/operators>:
>
> A function call with complex arguments (specifying arguments by keywords
> is highly recommended here):
>
> rect_1_pattern = \
> qah.Pattern.create_linear \
>   (
> p0 = (0, 0),
> p1 = (major_dim, 0),
> colour_stops =
> (
> (0, rect_1_colour),
> (1, complement(rect_1_colour)),
> )
>   )
>

I'd rather have intermediate variables and avoid the non-semantic
indentation.

p0 = (0, 0)
p1 = (major_dim, 0)
colour_stops = (0, rect_1_colour), (1, complement(rect_1_colour))
rect_1_pattern = qah.Pattern.create_linear(p0, p1, colour_stops)



Computing a variable value (using redundant parentheses to avoid
> backslash-continuations):
>
> dest_rect = \
> (
> draw_bounds
> +
> Vector(col, row) * draw_bounds.dimensions
> +
> Vector(0, top_extra)
> )
>

I'd rather have one long line for this case, even if it's "too long" by PEP
8 standards. If it's too long to think about, I'd break the task into
parts, each with a well-considered variable name.

substep = a + b
final = substep + c



From , a
> complex condition (with redundant parentheses again):
>
> if (
> not isinstance(src, Image)
> or
> mask != None and not isinstance(mask, Image)
> or
> not isinstance(dest, Image)
> ) :
> raise TypeError("image args must be Image objects")
> #end if
>

No need for the separate calls to isinstance, nor the check for None.

if any(not isinstance(obj, Image) for obj in [src, mask, dest]):
...


If you prefer maps to comprehensions:

is_image = lambda obj: isinstance(obj, Image)
if any(map(is_image, [src, mask, dest])):
...
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Holding until next value change

2016-08-20 Thread andrzej . brozi
Hello

Perhaps this would suffice:

prev = None
for value in main_call():
if value==prev:
pass
else:
prev = value
if prev>0:
print('+v')
elif prev<0:
print('-v')
else:
print('0')

Of course this will work only if subsequent values are exactly the same.
If not - then "value==prev" should be replaced by some other test (for sign or 
for proximity).

Regards
Andrzej Brozi
-- 
https://mail.python.org/mailman/listinfo/python-list


Knowing which thread had the GIL before

2016-08-20 Thread Julien Kauffmann

Hi,

I've worked the past few days on a stastistical sampling profiling tool 
for an online Python 2.7 service that runs on Windows.


My approach so far is:
- I have a dedicated thread that sleeps most of the time and wakes up 
every n-th milliseconds.
- Whenever the thread wakes-up, it gets the current frame/callstack for 
all the active threads (using threading.enumerate()) and increments an 
occurence counter for each currently executed code path.
- When enough time has passed, all the collected samples are saved for 
analysis.


This works somehow, but I fear this technique isn't aligned with how 
threading works in Python where only one thread can run Python code at a 
given time (GIL).


Consider the following case:

- An application has 2 threads running.
- Thread A sleeps for 30 seconds.
- Thread B does some heavy computation (only Python code).

In this case, it is fairly obvious that most of the process execution 
time will be spent in thread B, which will likely have the GIL most of 
the time (since thread A is sleeping). However, when measuring the 
activity with the technique mentionned above, the sleep instruction in 
Thread B appears as the most costly code location, has it is present in 
every profiling sample.


I'd like to modify my approach above by only measuring the activity of 
the last active thread. Obviously, this is not as simple as calling 
`threading.current_thread()` because it will always give me the 
profiling thread which is currently executing.


Is there a way to know which thread had the GIL right before my 
profiling thread acquired it ? Perhaps through a C extension ? I've seen 
such profilers for Linux that take advantage of an ITIMER signal to do 
that. Sadly this is not an option on Windows.


Any feedback or remark concerning my technique is also welcome.

Thanks,

Julien.

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


Re: saving octet-stream png file

2016-08-20 Thread Random832
On Sat, Aug 20, 2016, at 03:50, Marko Rauhamaa wrote:
> 2'scomplement arithmetics is quite often taken advantage of in C
> programming. Unfortunately, with the castration of signed integers with
> the most recent C standards, 2's-complement has been dangerously broken.

No part of any version of the C standard has ever allowed signed integer
overflow to work as defined behavior the way a generation of programmers
assumed it did. What changed was advances in compiler optimization
technology, not a standards change.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: saving octet-stream png file

2016-08-20 Thread Grant Edwards
On 2016-08-19, Random832  wrote:
> On Fri, Aug 19, 2016, at 16:51, Lawrence D’Oliveiro wrote:
>> On Saturday, August 20, 2016 at 6:03:53 AM UTC+12, Terry Reedy wrote:
>> >
>> > An 'octet' is a byte of 8 bits.
>> 
>> Is there any other size of byte?
>
> Not very often anymore. Used to be some systems had 9-bit bytes, and of
> course a lot of communication protocols only supported 7-bit data bytes.
> "Byte" is a technical term in the C and C++ standards meaning the
> smallest addressable unit even if that is a larger word.

Last time I looked a lot of DSP chips still have "byte" sizes larger
than 8 bits.  IIRC, 16, 24, and 32 bits are common byte sizes.

Not that Python runs on any of them...

-- 
Grant Edwards   grant.b.edwardsYow! A can of ASPARAGUS,
  at   73 pigeons, some LIVE ammo,
  gmail.comand a FROZEN DAQUIRI!!

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


Re: saving octet-stream png file

2016-08-20 Thread Marko Rauhamaa
Random832 :

> On Sat, Aug 20, 2016, at 03:50, Marko Rauhamaa wrote:
>> 2'scomplement arithmetics is quite often taken advantage of in C
>> programming. Unfortunately, with the castration of signed integers
>> with the most recent C standards, 2's-complement has been dangerously
>> broken.
>
> No part of any version of the C standard has ever allowed signed
> integer overflow to work as defined behavior the way a generation of
> programmers assumed it did.

Standard or no, it was widely taken advantage of and very useful.

> What changed was advances in compiler optimization technology, not a
> standards change.

I wonder how much is gained by those optimizations. The loss to code
quality is significant. What C standards have done is they have all but
deprecated the use of signed integers. If you have to do integer
arithmetics, cast everything into unsigned first.

I think it's terrible that in C,

   x + y + z

might not yield

   x + y + z

even if all of

   { x, y, z, x + y + z }

are inside the valid signed integer range.


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


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Lawrence D’Oliveiro
On Sunday, August 21, 2016 at 12:48:46 AM UTC+12, Michael Selik wrote:
>
> On Fri, Aug 19, 2016 at 5:01 AM Lawrence D’Oliveiro wrote:
> 
>> It is handy to be able to keep complex expressions together sometimes,
>> when breaking them up would simply obscure their structure.
> 
> p0 = (0, 0)
> p1 = (major_dim, 0)
> colour_stops = (0, rect_1_colour), (1, complement(rect_1_colour))
> rect_1_pattern = qah.Pattern.create_linear(p0, p1, colour_stops)

That’s an example of what I mean about obscure structure.

>> From , a
>> complex condition (with redundant parentheses again):
>>
>> if (
>> not isinstance(src, Image)
>> or
>> mask != None and not isinstance(mask, Image)
>> or
>> not isinstance(dest, Image)
>> ) :
>> raise TypeError("image args must be Image objects")
>> #end if
>>
> 
> No need for the separate calls to isinstance, nor the check for None.
> 
> if any(not isinstance(obj, Image) for obj in [src, mask, dest]):
> ...

Spot the bug in your version...
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Lawrence D’Oliveiro
On Friday, August 19, 2016 at 8:56:31 PM UTC+12, I wrote:
> It is handy to be able to keep complex expressions together sometimes, when
> breaking them up would simply obscure their structure. To avoid lines
> getting long, why not take advantage of the two available screen/page
> dimensions to make their structure clearer? As a bonus, spacing out
> parentheses makes them look less of a clutter.

Another example, from : the sequence of values 
is laid out to allow easy additions/modifications in future.

for \
symname, funcname \
in \
(
("FC_FONT", "ft_font_face_create_for_ft_face"),
("FT_FONT", "ft_font_face_create_for_pattern"),
("IMAGE_SURFACE", "image_surface_create"),
# TODO: MIME_SURFACE, OBSERVER_SURFACE?
("PDF_SURFACE", "pdf_surface_create"),
("PNG_FUNCTIONS", "surface_write_to_png"),
("PS_SURFACE", "ps_surface_create"),
("RECORDING_SURFACE", "recording_surface_create"),
("SCRIPT_SURFACE", "script_create"),
("SVG_SURFACE", "svg_surface_create"),
{"USER_FONT", "user_font_face_create"},
) \
:
setattr \
  (
HAS,
symname,
hasattr(cairo, "cairo_" + funcname)
  )
#end for

As a bonus, this also counts as an example of data-driven programming.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Two-Dimensional Expression Layout

2016-08-20 Thread cs

On 19Aug2016 16:11, Lawrence D’Oliveiro  wrote:

On Saturday, August 20, 2016 at 10:38:34 AM UTC+12, Chris Angelico wrote:

On Sat, Aug 20, 2016 at 8:31 AM, Lawrence D’Oliveiro wrote:

There is no short-cut evaluation when constructing tuples and lists.


I'm not sure how that would make difference in these examples. The
three parts are independent - the one place where short-circuiting is
important is indeed short-circuited.


That often is not the case, e.g. 
:

   assert \
   (
   len(self.points) == 0
   or
   not self.points[0].off
   and
   (closed or not self.points[-1].off)
   )


Aye, but beware that the expression is actually correct for the indentation.  
Compare:


  assert \
  (
  len(self.points) == 0
  and
  not self.points[0].off
  or
  (closed or not self.points[-1].off)

where the precedence causes the layout to mislead.

I'm not arguing against indented spread out layout here, I use it myself, but 
just mentioning that the human eye will tend to take the visual layout over a 
strict parse. So care is needed, as in all programming.


Cheers,
Cameron Simpson 
--
https://mail.python.org/mailman/listinfo/python-list


Re: The Joys Of Data-Driven Programming

2016-08-20 Thread Lawrence D’Oliveiro
On Saturday, August 20, 2016 at 8:08:24 PM UTC+12, Marko Rauhamaa wrote:
>
> Lawrence D’Oliveiro:
> 
>> On Thursday, August 18, 2016 at 4:47:28 PM UTC+12, Marko Rauhamaa wrote:
>>>
>>> ... as a rule, I dislike rules. Rule languages tend to
>>> grow out of all bounds, always remain deficient and have impenetrable,
>>> ad-hoc semantics.
>>
>> That’s a very peculiar thing to say, considering that data-driven
>> programming is a well-known technique for writing compact code.
>>
>> Less code, and in particular, less repetitive code => fewer bugs.
> 
> I can't relate to what you say.
> 
> All I can say is that I've encountered numerous bad cases of rule
> systems, eg:
> 
>  - iptables
> 
>  - selinux policies
> 
>  - systemd unit files
> 
>  - asterisk
> 
>  - sendmail

I can’t relate to you, either. All those are spectacularly successful examples 
of highly-configurable pieces of software.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Lawrence D’Oliveiro
On Sunday, August 21, 2016 at 10:35:08 AM UTC+12, c...@zip.com.au wrote:
> Aye, but beware that the expression is actually correct for the
> indentation.  
> Compare:
> 
>assert \
>(
>len(self.points) == 0
>and
>not self.points[0].off
>or
>(closed or not self.points[-1].off)
> 
> where the precedence causes the layout to mislead.

At least there is a discrepancy between the two to set alarm bells ringing.

Compare statement indentation, where Python got rid of the statement brackets, 
so there is no more redundancy to be checked.

Why do you think I put in those “#end” lines?
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Michael Selik
On Sat, Aug 20, 2016 at 6:21 PM Lawrence D’Oliveiro 
wrote:

> > p0 = (0, 0)
> > p1 = (major_dim, 0)
> > colour_stops = (0, rect_1_colour), (1, complement(rect_1_colour))
> > rect_1_pattern = qah.Pattern.create_linear(p0, p1, colour_stops)
>
> That’s an example of what I mean about obscure structure.
>

To each his own. I was assuming all those variable names meant something to
you. If not, then I expect it'd read well with good names. In this example,
I think the abbreviations and numbers in the names could be changed to
something more meaningful.


> >> From , a
> >> complex condition (with redundant parentheses again):
> >>
> >> if (
> >> not isinstance(src, Image)
> >> or
> >> mask != None and not isinstance(mask, Image)
> >> or
> >> not isinstance(dest, Image)
> >> ) :
> >> raise TypeError("image args must be Image objects")
> >> #end if
> >>
> >
> > No need for the separate calls to isinstance, nor the check for None.
> >
> > if any(not isinstance(obj, Image) for obj in [src, mask, dest]):
> > ...
>
> Spot the bug in your version...
>

It'd be easier if I ran the code :-)
Let's see...
- the ``or`` translates to an ``any(...)``
- ``not isinstance(obj, Image)`` is repeated 3 times
- ``[src, mask, dest]`` corresponds to the 3 objects
- ``mask != None`` is unnecessary, unless somehow None has been registered
as an instance of Image.

... can't spot it. Give me a hint?
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Michael Selik
On Sat, Aug 20, 2016 at 8:43 PM Michael Selik 
wrote:

> On Sat, Aug 20, 2016 at 6:21 PM Lawrence D’Oliveiro <
> lawrenced...@gmail.com> wrote:
>
>> > p0 = (0, 0)
>> > p1 = (major_dim, 0)
>> > colour_stops = (0, rect_1_colour), (1, complement(rect_1_colour))
>> > rect_1_pattern = qah.Pattern.create_linear(p0, p1, colour_stops)
>>
>> That’s an example of what I mean about obscure structure.
>>
>
> To each his own. I was assuming all those variable names meant something
> to you. If not, then I expect it'd read well with good names. In this
> example, I think the abbreviations and numbers in the names could be
> changed to something more meaningful.
>

I think that came out wrong. Let me try again...

origin = 0, 0
destination = width, 0
start_color = 0, selected_color
stop_color = 1, complement(selected_color)
pattern = qah.Pattern.from_line(origin, destination, (start_color,
stop_color))

Better?
I wasn't sure what the numbers 0 and 1 are doing for the colour_stops.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Steve D'Aprano
On Sun, 21 Aug 2016 08:22 am, Lawrence D’Oliveiro wrote:

> Another example, from : the sequence of
> values is laid out to allow easy additions/modifications in future.

When replying, I normally try to trim unnecessary code snippets down to the
critical line or two, but in this case I think that it is important that I
leave Lawrence's example in place in all its glory. See below for further
comments.


> for \
> symname, funcname \
> in \
> (
> ("FC_FONT", "ft_font_face_create_for_ft_face"),
> ("FT_FONT", "ft_font_face_create_for_pattern"),
> ("IMAGE_SURFACE", "image_surface_create"),
> # TODO: MIME_SURFACE, OBSERVER_SURFACE?
> ("PDF_SURFACE", "pdf_surface_create"),
> ("PNG_FUNCTIONS", "surface_write_to_png"),
> ("PS_SURFACE", "ps_surface_create"),
> ("RECORDING_SURFACE", "recording_surface_create"),
> ("SCRIPT_SURFACE", "script_create"),
> ("SVG_SURFACE", "svg_surface_create"),
> {"USER_FONT", "user_font_face_create"},
> ) \
> :
> setattr \
>   (
> HAS,
> symname,
> hasattr(cairo, "cairo_" + funcname)
>   )
> #end for
> 
> As a bonus, this also counts as an example of data-driven programming.


Is the subtle bug in your code also a bonus?

If this bug has never bit you, it will when you try to run it under a
version of Python with hash randomization turned on. (3.5 and above, I
think.) You're (accidentally, I presume) relying on the set:

{"USER_FONT", "user_font_face_create"}

always iterating in the same order. It won't. I assume that's just a typo
and it's meant to be a tuple.

Your idiosyncratic layout obscures what should be a standard two-line for
loop in a jumble of unneeded backslashes, almost empty lines and
indentation.


for symname, funcname in FONT_TABLE:
setattr(HAS, symname, hasattr(cairo, "cairo_" + funcname))


where FONT_TABLE is defined previously. If you don't want to give this its
own name, you can embed it in the for loop:


for symname, funcname in [
("FC_FONT", "ft_font_face_create_for_ft_face"),
("FT_FONT", "ft_font_face_create_for_pattern"),
("IMAGE_SURFACE", "image_surface_create"),
# TODO: MIME_SURFACE, OBSERVER_SURFACE?
("PDF_SURFACE", "pdf_surface_create"),
("PNG_FUNCTIONS", "surface_write_to_png"),
("PS_SURFACE", "ps_surface_create"),
("RECORDING_SURFACE", "recording_surface_create"),
("SCRIPT_SURFACE", "script_create"),
("SVG_SURFACE", "svg_surface_create"),
("USER_FONT", "user_font_face_create"),
]:
setattr(HAS, symname, hasattr(cairo, "cairo_" + funcname))



There's no need to arbitrarily indent parts of expressions to "allow easy
additions" in the future: it is already easy to add new tuples to the
table, or modify existing ones.



-- 
Steve
“Cheer up,” they said, “things could be worse.” So I cheered up, and sure
enough, things got worse.

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


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Steve D'Aprano
On Sun, 21 Aug 2016 09:44 am, Lawrence D’Oliveiro wrote:

> Why do you think I put in those “#end” lines?


Do you really want us to answer that? I don't think you will like the
answer.





-- 
Steve
“Cheer up,” they said, “things could be worse.” So I cheered up, and sure
enough, things got worse.

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


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Steve D'Aprano
On Sun, 21 Aug 2016 10:43 am, Michael Selik wrote:

> On Sat, Aug 20, 2016 at 6:21 PM Lawrence D’Oliveiro
>  wrote:
> 
>> > p0 = (0, 0)
>> > p1 = (major_dim, 0)
>> > colour_stops = (0, rect_1_colour), (1, complement(rect_1_colour))
>> > rect_1_pattern = qah.Pattern.create_linear(p0, p1, colour_stops)
>>
>> That’s an example of what I mean about obscure structure.
>>
> 
> To each his own. I was assuming all those variable names meant something
> to you. If not, then I expect it'd read well with good names. In this
> example, I think the abbreviations and numbers in the names could be
> changed to something more meaningful.
> 
> 
>> >> From , a
>> >> complex condition (with redundant parentheses again):
>> >>
>> >> if (
>> >> not isinstance(src, Image)
>> >> or
>> >> mask != None and not isinstance(mask, Image)
>> >> or
>> >> not isinstance(dest, Image)
>> >> ) :
>> >> raise TypeError("image args must be Image objects")
>> >> #end if
>> >>
>> >
>> > No need for the separate calls to isinstance, nor the check for None.
>> >
>> > if any(not isinstance(obj, Image) for obj in [src, mask, dest]):
>> > ...
>>
>> Spot the bug in your version...
>>
> 
> It'd be easier if I ran the code :-)
> Let's see...
> - the ``or`` translates to an ``any(...)``
> - ``not isinstance(obj, Image)`` is repeated 3 times
> - ``[src, mask, dest]`` corresponds to the 3 objects
> - ``mask != None`` is unnecessary, unless somehow None has been registered
> as an instance of Image.
> 
> ... can't spot it. Give me a hint?

Earlier, Lawrence wrote about this same piece of code that using any() or
all() was not a good idea because, and I quote:

"There is no short-cut evaluation when constructing tuples and lists."

I think that he is envisaging a scenario where (say) src and mask are
defined, but dest is not, so 

[src, mask, dest]

will raise a NameError, but his earlier version of the code:


if (
not isinstance(src, Image)
or
mask != None and not isinstance(mask, Image)
or
not isinstance(dest, Image)
) :


will not, *provided* one of the tests on src or mask fail first.





-- 
Steve
“Cheer up,” they said, “things could be worse.” So I cheered up, and sure
enough, things got worse.

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


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Steve D'Aprano
Oh wait! The penny drops!

On Sun, 21 Aug 2016 10:43 am, Michael Selik wrote:

> On Sat, Aug 20, 2016 at 6:21 PM Lawrence D’Oliveiro

>> >> if (
>> >> not isinstance(src, Image)
>> >> or
>> >> mask != None and not isinstance(mask, Image)
>> >> or
>> >> not isinstance(dest, Image)
>> >> ) :
>> >> raise TypeError("image args must be Image objects")
>> >> #end if
>> >>
>> >
>> > No need for the separate calls to isinstance, nor the check for None.
>> >
>> > if any(not isinstance(obj, Image) for obj in [src, mask, dest]):
>> > ...
>>
>> Spot the bug in your version...
>>
> 
> It'd be easier if I ran the code :-)
> Let's see...
> - the ``or`` translates to an ``any(...)``
> - ``not isinstance(obj, Image)`` is repeated 3 times
> - ``[src, mask, dest]`` corresponds to the 3 objects
> - ``mask != None`` is unnecessary, unless somehow None has been registered
> as an instance of Image.
> 
> ... can't spot it. Give me a hint?

I think you've got the mask != None bit backwards. In Lawrence's version, if
mask is None, *no exception is raised*. In yours, it raises.

I think that it would be easier to reason about this code if it were written
in terms of positive assertions ("this condition is true") rather than
negative ("this condition is not true").

- src must be an Image;
- mask must be None or an Image;
- dest must be an Image.

Assuming I check for this in at least two places, I'd factor it out into a
helper function. There are probably a thousand ways to write it, and I'm
not married to any of them. Here are a couple:


def _validate(src, mask, dest):
if mask is None or isinstance(mask, Image) and \
all(isinstance(o) for o in [src, dest]):
return
raise TypeError("image args must be Image objects")


def _validate(src, mask, dest):
if not (
isinstance(src, Image) and
mask is None or isinstance(mask, Image) and 
isinstance(dest, Image)
   ):
raise TypeError("image args must be Image objects")


The logic is *just* tricky enough that if this were my code I would
absolutely insist on having unit tests for this helper. Beyond that, the
specific details of how you test them is not that important, but given that
there are only three arguments to be tested, I'm inclined to test each one
individually and give a more useful error message:

def _validate(src, mask, dest):
if not isinstance(src, Image):
raise TypeError("src must be an Image")
if mask is not None and not isinstance(mask, Image):
raise TypeError("mask must be None or an Image")
if not isinstance(dest, Image):
raise TypeError("dest must be an Image")




-- 
Steve
“Cheer up,” they said, “things could be worse.” So I cheered up, and sure
enough, things got worse.

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


Good Tutorial for Python3 winreg Module

2016-08-20 Thread johncalvinhall
Does anyone have a good tutorial on how to use the Python 3 module
winreg?

I need to pull a saved value from the registry, and the only way I
know how to get it is through winreg.

If anyone is able to help, I sure would appreciate it.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Lawrence D’Oliveiro
On Sunday, August 21, 2016 at 12:44:21 PM UTC+12, Michael Selik wrote:
>
> On Sat, Aug 20, 2016 at 6:21 PM Lawrence D’Oliveiro wrote:
> 
>>> if any(not isinstance(obj, Image) for obj in [src, mask, dest]):
>>> ...
>>
>> Spot the bug in your version...
> 
> - ``mask != None`` is unnecessary, unless somehow None has been registered
> as an instance of Image.

That’s the bug: it’s not unnecessary.

Maybe a quick application of one of De Morgan’s theorems might help:

if (
isinstance(src, Image)
and
(mask == None or isinstance(mask, Image))
and
isinstance(dest, Image)
) :
don’t raise TypeError("image args must be Image objects")
#end if

Is that better for you?
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Good Tutorial for Python3 winreg Module

2016-08-20 Thread eryk sun
On Sun, Aug 21, 2016 at 3:55 AM,   wrote:
>
> I need to pull a saved value from the registry, and the only way I
> know how to get it is through winreg.

Here's an example that reads the value and type of "Temp" in HKCU\Environment:

import winreg

with winreg.OpenKey(winreg.HKEY_CURRENT_USER, 'Environment') as key:
value, dtype = winreg.QueryValueEx(key, 'Temp')

>>> print(value)
%USERPROFILE%\AppData\Local\Temp
>>> dtype == winreg.REG_EXPAND_SZ
True

I can help more if you provide a specific example of the value that
you need to read.
-- 
https://mail.python.org/mailman/listinfo/python-list


Re: Two-Dimensional Expression Layout

2016-08-20 Thread Michael Selik
On Sun, Aug 21, 2016 at 12:31 AM Lawrence D’Oliveiro 
wrote:

> On Sunday, August 21, 2016 at 12:44:21 PM UTC+12, Michael Selik wrote:
> >
> > On Sat, Aug 20, 2016 at 6:21 PM Lawrence D’Oliveiro wrote:
> >
> >>> if any(not isinstance(obj, Image) for obj in [src, mask, dest]):
> >>> ...
> >>
> >> Spot the bug in your version...
> >
> > - ``mask != None`` is unnecessary, unless somehow None has been
> registered
> > as an instance of Image.
>
> That’s the bug: it’s not unnecessary.
>
> Maybe a quick application of one of De Morgan’s theorems might help:
>
> if (
> isinstance(src, Image)
> and
> (mask == None or isinstance(mask, Image))
> and
> isinstance(dest, Image)
> ) :
> don’t raise TypeError("image args must be Image objects")
> #end if
>
> Is that better for you?
>

Indeed it is, not sure why. I think Steven's right in this case. Since the
condition isn't identical for all objects, and it's only three variables,
I'd rather break it apart.

if not isinstance(src, Image):
raise TypeError('src must be an Image')
if mask and not isinstance(mask, Image):
raise TypeError('mask must be an Image or None')
if not isinstance(dest, Image):
raise TypeError('dest must be an Image')

As he said as well, this has the added benefit of encouraging more explicit
error messages.

In programming and in prose, sometimes repetition feels ugly and redundant,
but sometimes repetition feels like a beautiful harmony.
-- 
https://mail.python.org/mailman/listinfo/python-list