Le 15/06/2024 à 02:49, Koichi Murase écrivait :
2024年6月14日(金) 16:18 Léa Gris <lea.g...@noiraude.net>:
Another elegant option would be to expand the existing variables' i flag
to tell the variable is numeric rather than integer.

Then have printf handle argument variables with the numeric flag as
using the LC_NUMERIC=C floating-point format with dot radix point.

In that design, how does the `printf' builtin know that the argument
string is generated by a specific variable with the numeric flag?  The
`printf' builtin is a (builtin) command that receives arguments as
strings.  The arguments do not carry the contexts of how the strings
are generated, (though some of the exceptions are the array
assignments of the assignment builtins).

Indeed printf only knows the string value. But Bash know the variable has a numeric flag when doing the value expansion, so it expands it using the current LC_NUMERIC locale in this specific case.


# Numeric format use comma as radix separator
LC_NUMERIC=fr_FR.UTF8

# Numeric variable uses the C locale format internally
declare -i floatVar=3.1415

# Printf does not have to know about the variable type
# as it is expanded in the current LC_NUMERIC format
printf '%.2f\n' "$floatVar"
# Prints 3,14

# Same when it is expanded to assign another variable
# stringVar=3,1415
# Since the string expansion of numeric variable uses the
# LC_NUMERIC format
stringVar=$floatVar

# Same rule applies when expanding a numerical context to a string:
echo "$((2 * 3.14))"
# Prints the string 6,28 because LC_NUMERIC=fr_FR.UTF8

# Do not use string expansion to assign numeric value or it will fail
# with different locale. Use a numeric context to assign.
# Do:
(( arc = 2 * floatVar ))
# Don't:
# arc=$((2 * floatVar ))

# Note that the numeric flag is not needed within a numeric context
echo "$arc"
# Prints 6.283 because arc has no numeric flag
# so it is expanded verbatin to string
echo "$((arc))"
# Prints 6,283 because the implied numerical context
# expands the value using LC_NUMERIC format

--
Léa Gris

Reply via email to