New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
SvNV() does not store computed value to NV slot #15875
Comments
From @paliWhen sv is non-magic PV type then functions SvIV(), SvUV() and SvNV() But SvNV() does not upgrade sv if is magical. And converted value is It is in function Perl_sv_2nv_flags() (called by SvNV() on sv of PV On the other hand Perl_sv_2iv_flags() (called by SvIV()) calls So is there reason why SvNV() behave differently for magic scalars? Or |
From @khwilliamsonI don't have an answer to this question, but I can tell you why a stringified NV isn't stored. It is because the radix character varies by locale. In Czech, I believe it is a comma; in English, a period. And if the locale changes the character changes, and a PV that was generated in a different locale will be invalid. There were various bug tickets filed because of this. so we stopped storing the stringified number. Another approach would be to attach magic to it, like we do now to PVs that have been collated. The magic knows what locale was used for the stringification, and if the locale changes (reasonably unlikely) invalidate the PV. Karl Williamson |
The RT System itself - Status changed from 'new' to 'open' |
From @paliOn Monday 20 February 2017 23:36:46 you wrote:
But here it is reverse situation: Numerification of string (convert PV And current behaviour is that NV value (converted from string PV) is
Yes IIRC it is. But I have never seen perl to print me comma in any
Is locale valid also for this reverse situation? |
From @andk
> Yes IIRC it is. But I have never seen perl to print me comma in any LC_ALL=de_DE.UTF-8 perl -le 'use locale; print 0.42'
> Is locale valid also for this reverse situation? Not sure I understand your question. Maybe you mean this: LC_ALL=cs_CZ.UTF-8 perl -le 'use locale; print "0.42"+0' -- |
From @paliOn Monday 20 February 2017 19:12:09 (Andreas J. Koenig) via RT wrote:
Ah, I forgot 'use locale;' when testing. But back to my question, do you know why behaviour is different for |
From @tonycozOn Tue, 21 Feb 2017 01:43:35 -0800, pali@cpan.org wrote:
I'm pretty sure storing the NV as we currently do is a bug: $ LANG=de_DE.utf8 ./perl -Ilib -Mlocale -le '$x = "0,42"; print $x+0; no locale; print $x+0' $ LANG=de_DE.utf8 ./perl -Ilib -le '$x = "5,42"; print $x+0;' From the discussion in #p5p, is this still an issue for you? Tony |
From @paliOn Monday 27 February 2017 16:00:00 Tony Cook via RT wrote:
So it means that SvNV() should not store computed value to NV slot, right?
And then it is different bug...
So from discussion I understood that SvNV(), SvIV() and SvUV() does not I'm ok with it but I would suggest to explicitly document this behaviour |
From @paliOn Tuesday 28 February 2017 14:22:25 pali@cpan.org wrote:
In attachment is proposed patch for this documentation change. |
From @pali0001-perlapi-Clarify-SvIV-SvUV-SvNV-behavior.patchFrom 340a389aa37b76c808ed3f59cb35d530eb641bc3 Mon Sep 17 00:00:00 2001
From: Pali <pali@cpan.org>
Date: Sun, 5 Mar 2017 11:35:51 +0100
Subject: [PATCH] perlapi: Clarify SvIV/SvUV/SvNV behavior
---
sv.h | 33 ++++++++++++++++++---------------
1 file changed, 18 insertions(+), 15 deletions(-)
diff --git a/sv.h b/sv.h
index 6227d46..a8fc09e 100644
--- a/sv.h
+++ b/sv.h
@@ -1517,42 +1517,45 @@ Like C<SvPV> but doesn't set a length variable.
Like C<SvPV_nolen> but doesn't process magic.
=for apidoc Am|IV|SvIV|SV* sv
-Coerces the given SV to an integer and returns it. See C<L</SvIVx>> for a
-version which guarantees to evaluate C<sv> only once.
+Coerces the given SV to IV and returns it. Computed value does not have to be
+stored in C<sv>'s IV slot (use C<L</sv_setiv>> for it). See C<L</SvIVx>> for
+a version which guarantees to evaluate C<sv> only once.
=for apidoc Am|IV|SvIV_nomg|SV* sv
Like C<SvIV> but doesn't process magic.
=for apidoc Am|IV|SvIVx|SV* sv
-Coerces the given SV to an integer and returns it.
-Guarantees to evaluate C<sv> only once. Only use
-this if C<sv> is an expression with side effects,
+Coerces the given SV to IV and returns it. Computed value does not have to be
+stored back to C<sv> (use C<L</sv_setiv>> for it). Guarantees to evaluate
+C<sv> only once. Only use this if C<sv> is an expression with side effects,
otherwise use the more efficient C<SvIV>.
=for apidoc Am|NV|SvNV|SV* sv
-Coerce the given SV to a double and return it. See C<L</SvNVx>> for a version
-which guarantees to evaluate C<sv> only once.
+Coerces the given SV to NV and returns it. Computed value does not have to be
+stored back to C<sv> (use C<L</sv_setnv>> for it). See C<L</SvNVx>> for
+a version which guarantees to evaluate C<sv> only once.
=for apidoc Am|NV|SvNV_nomg|SV* sv
Like C<SvNV> but doesn't process magic.
=for apidoc Am|NV|SvNVx|SV* sv
-Coerces the given SV to a double and returns it.
-Guarantees to evaluate C<sv> only once. Only use
-this if C<sv> is an expression with side effects,
+Coerces the given SV to NV and returns it. Computed value does not have to be
+stored back to C<sv> (use C<L</sv_setnv>> for it). Guarantees to evaluate
+C<sv> only once. Only use this if C<sv> is an expression with side effects,
otherwise use the more efficient C<SvNV>.
=for apidoc Am|UV|SvUV|SV* sv
-Coerces the given SV to an unsigned integer and returns it. See C<L</SvUVx>>
-for a version which guarantees to evaluate C<sv> only once.
+Coerces the given SV to UV and returns it. Computed value does not have to be
+stored back to C<sv> (use C<L</sv_setuv>> for it). See C<L</SvUVx>> for
+a version which guarantees to evaluate C<sv> only once.
=for apidoc Am|UV|SvUV_nomg|SV* sv
Like C<SvUV> but doesn't process magic.
=for apidoc Am|UV|SvUVx|SV* sv
-Coerces the given SV to an unsigned integer and
-returns it. Guarantees to evaluate C<sv> only once. Only
-use this if C<sv> is an expression with side effects,
+Coerces the given SV to UV and returns it. Computed value does not have to be
+stored back to C<sv> (use C<L</sv_setuv>> for it). Guarantees to evaluate
+C<sv> only once. Only use this if C<sv> is an expression with side effects,
otherwise use the more efficient C<SvUV>.
=for apidoc Am|bool|SvTRUE|SV* sv
--
1.7.9.5
|
From @khwilliamsonThanks, applied as 04e8f31 |
@khwilliamson - Status changed from 'open' to 'resolved' |
From @demerphqOn 20 February 2017 at 23:36, Karl Williamson via RT
Is there a reason we cannot make this "no-cache" behavior "use locale" specific? For instance I would have thought the logic would be: if under "use cheers, -- |
From zefram@fysh.orgdemerphq wrote:
Yes: getting different stringifications arises from two stringification $ LANG=de_DE perl -lwe '$a = 1.5; print "$a"; { use locale; print "$a"; }'
You seem to be imagining that "use locale" is a global flag affecting -zefram |
From @demerphqOn 12 Apr 2017 11:56, "Zefram" <zefram@fysh.org> wrote: demerphq wrote:
Yes: getting different stringifications arises from two stringification $ LANG=de_DE perl -lwe '$a = 1.5; print "$a"; { use locale; print "$a"; }' I feel like you did not read what I wrote. This example does not
You seem to be imagining that "use locale" is a global flag affecting Yes. I get that. So what? If there is a flag or function that's says 'use locale' is in effect, and |
From @cpansproutOn Wed, 12 Apr 2017 10:56:42 -0700, demerphq wrote:
How would we distinguish between an NV that got stringified outside of ‘use locale’ and a string that got numified at some point? Presumably we would use just SVp_POK, not SVf_POK, for a stringified NV. -- Father Chrysostomos |
From @demerphqOn 12 Apr 2017 23:24, "Father Chrysostomos via RT" < On Wed, 12 Apr 2017 10:56:42 -0700, demerphq wrote:
How would we distinguish between an NV that got stringified outside of ‘use Do you forsee any difference with current behaviour? As far as I understand Yved |
From @demerphqOn 21 February 2017 at 04:11, Andreas Koenig
Curiously this does not work for me: $ LC_ALL=de_DE.UTF-8 perl -le 'use locale; print 0.42' Do you know what I might have to do to replicate? I installed the Yves |
From @esertedemerphq <demerphq@gmail.com> writes:
Which perl version? You need 5.20 or later: $ for i in /opt/perl-5.*/bin/perl; do echo -n "$i: "; LC_ALL=de_DE.UTF-8 $i -le 'use locale; print 0.42'; done -- Berlin Perl Mongers - http://berlin.pm.org |
From @demerphqOn 12 April 2017 at 23:21, Father Chrysostomos via RT
I assume the semantics would be the same as they are now. But i can't I guess it comes down to what the following could should and does do: LC_ALL=de_DE.UTF-8 perl -le 'my $f= "0.42"; print 0+$f; { use locale; If that prints: then under my proposal things would work the same as they do now. If that prints: Then IMO the current behavior is insane and we should just the revert I am assuming that we all agree it *should* output like the first set, Yves Yves -- |
From @demerphqOn 13 April 2017 at 09:05, demerphq <demerphq@gmail.com> wrote:
Color me very very surprised: $ LC_ALL=de_DE.UTF-8 perl -le 'my $f= "0.42"; print 0+$f; { use locale;
Even worse: $ LC_ALL=de_DE.UTF-8 perl -le 'my $f1= "0.42"; my $f2; print 0+$f1; { IMO these are completely broken semantics. Removing caching/promotion cheers, -- |
From zefram@fysh.orgdemerphq wrote:
No, we do not. If a scalar has a PV, we use its PV whenever a PV is $ perl -MDevel::Peek=Dump -lwe '$a = "1.50"; print $a + 0.25; print $a; Dump $a' Here the PV "1.50" is used for the second print, even though the scalar To cache the non-locale stringification of an NV would be quite different -zefram |
From zefram@fysh.orgdemerphq wrote:
That would be insane semantics. That would mean that computing the
That is what it does print. I don't see the insanity. I see semantics
I particularly don't see how you can blame caching semantics for any
No, we do not.
Yes. The fact that the stringification depends on locale settings breaks The change in 5.20 from having the locale for stringification depend -zefram |
From @demerphqThank you for setting me straight. I see my definition of insane is Yves On 13 April 2017 at 11:33, Zefram <zefram@fysh.org> wrote:
-- |
From @khwilliamsonOn 04/13/2017 03:33 AM, Zefram wrote:
I don't understand what you mean here about strange. Did you have a commit c8f77a9 * Merge LC_NUMERIC locale changes branch into blead LC_NUMERIC hasn't been implemented quite the same way as the other There are two possible implemantation paths that come to my mind Unfortunately the implementation (prior to this series of commits) In any event, there has long been infrastructure that facilitates What I've done here is move to the first implementation path mentioned |
From @khwilliamsonOn 04/13/2017 11:32 AM, Karl Williamson wrote:
And this came about because of: commit bc8ec7c PATCH: [perl #120723] Setting LC_NUMERIC breaks parsing of constants This is the final patch for [perl #120723], and adds tests for it. LC_NUMERIC Locale handling was broken for code during the |
From zefram@fysh.orgKarl Williamson wrote:
I meant that it has a strange status with respect to those issues of the
I haven't narrowed it down to a specific commit. The one you identify $ LANG=de_DE perl5.19.7 -MPOSIX=setlocale,LC_ALL -lwe '{ use locale; print 1.5; } setlocale(LC_ALL, ""); print 1.5;' -zefram |
From @cpansproutOn Wed, 12 Apr 2017 23:44:50 -0700, demerphq wrote:
It looks to me as though this scalar is still POK: $ perl5.24.0 -MDevel::Peek -e '$x = "1.3"; 0+$x; Dump $x' -- Father Chrysostomod |
From @cpansproutOn Thu, 13 Apr 2017 00:17:01 -0700, demerphq wrote:
That is what I would expect. At no point did you assign a value to $f other than the string "0.42". (I do agree, though, that locales are fundamentally incompatible with Perl’s scalar model.)
Again, that is what I would expect. As long as I assign the string "0.42" to a scalar, I want it stringified exactly the same way, regardless of what contexts I might have used it in, even if we are under a different locale. I do not disagree that the semantics are broken, though. The whole locale model should have been better thought through and probably provided as a functional interface, rather than a change in the way scalars behave.
-- Father Chrysostomos |
From @demerphqOn 13 April 2017 at 22:55, Father Chrysostomos via RT
Yes, once you take the position that "the original string should be
Thanks. This is what I should have said myself. Yves |
Migrated from rt.perl.org#130801 (status was 'resolved')
Searchable as RT130801$
The text was updated successfully, but these errors were encountered: