-
-
Notifications
You must be signed in to change notification settings - Fork 30.1k
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
gettext: deprecate selecting plural form by fractional numbers #72878
Comments
GNU gettext library accepts only integer value for selecting plural form. Python gettext accepts arbitrary numbers. But gettext formulas are not purposed to support non-integer values and can return incorrect result. For example (in Ukrainian): "1 площа", but "1.5 площі", not "1.5 площ". Separate plural form should be used for fractional numbers. Even if fractional part happens to be zero, it is acceptable (e.g. "Time elapsed: 1.000 seconds" in English). Proposed patch deprecates fractional numbers for selecting plural form in gettext. |
Hi, did you forget to attach the patch? |
Sorry. Here is a patch. |
Maybe you have forgotten to remove the debug print in the patch? |
Yes, of cause. Thank your for noticing this. |
I think the stacklevel should be 3. stacklevel = 3: ./python -Walways /tmp/a.py stacklevel = 4: ./python -Walways /tmp/a.py |
Ohh, sorry. It should be 4 and I make a mistake. Sorry for the noise. Patch LGTM. |
Looks like the cast to integer is done *before* giving the value to the C gettext expression.
As long as gettext expression don't support non-integer values, there exist *no* way to support two languages where plural form differ for non-integer value. Typically if a language A consider 1.5 to be singular and another language B consider 1.5 to be plural, the only place in the code that can make the difference IS in the C plural expression which don't support non-integer values. Rouding the value before giving it to ngettext only fixes the issue for the lang of the current developer, as for other languages, translators won't be able to change the rounding properties. But should we bet that in most, any, or all languages, 1.5 is considered plural? I think so, according to wikipedia¹: "Plural of nouns typically denote a quantity other than the default quantity represented by a noun, which is generally one." So, I think that a better fix than warning for non-integer values may be to round them using math.ceil instead of round. This way we avoid developpers to drop round() everywhere to fix the warning the wrong way, leaving the same bug you're having in Ukrainian. |
round() was used because it is the simplest way to convert fractional numbers to integers that doesn't involve strings-to-integer converting (as in int()). Perhaps math.trunc() looks a little more appropriate. math.ceil() returns a float in 2.7 and is limited by float range. But "1.678 second" don't look more correct than "1.678 seconds". My point is that gettext ability of selecting plural form shouldn't be used for fractional numbers. It seems to me that a fractional number should be formatted with the same form independently from it's value (it can be different from plural forms for integer numbers). Proposed patch adds a deprecating warning for encouraging users to rewrite their code for formatting fractional numbers. |
Ok, so 1.000 seconds, ok, LGTM. Should we mention something explicit about it? Not sure how to write it down, but I still fear that everyone's reaction will be "Oh can't give a float? Let my put a round() in my call" and stay with the same plural bug as before. Maybe replace
by
? |
Follow-up issue #94194: gettext: Remove support for using non-integer value for selecting a plural form. |
Note: these values reflect the state of the issue at the time it was migrated and might not reflect the current state.
Show more details
GitHub fields:
bugs.python.org fields:
The text was updated successfully, but these errors were encountered: