[llvm] [APFloat] Add APFloat::format (PR #99088)
Matt Arsenault via llvm-commits
llvm-commits at lists.llvm.org
Tue Oct 8 00:28:52 PDT 2024
================
@@ -1378,6 +1378,171 @@ TEST(APFloatTest, toString) {
}
}
+TEST(APFloatTest, format) {
+ auto doit_precision = [](const fltSemantics &S, const char *value,
+ llvm::FloatStyle style, int precision,
+ const char *expected) {
+ SmallString<16> s;
+ APFloat apf(S, value);
+ apf.format(s, style, precision);
+ EXPECT_STREQ(expected, s.c_str());
+ };
+ auto doit = [](const fltSemantics &S, const char *value,
+ llvm::FloatStyle style, const char *expected) {
+ SmallString<16> s;
+ APFloat apf(S, value);
+ apf.format(s, style);
+ EXPECT_STREQ(expected, s.c_str());
+ };
+
+ // default precision for Exponent and ExponentUpper is 6
+ // and 2 for Fixed and Psercent
+ // All float formats should be able to handle small vlues.
+ // The smaller formats, like float8, are more restricted.
+ for (unsigned I = 0; I != APFloat::S_MaxSemantics + 1; ++I) {
+ auto SemEnum = static_cast<APFloat::Semantics>(I);
+ const auto &S = APFloat::EnumToSemantics(SemEnum);
+ auto Precision = APFloat::semanticsPrecision(S);
+
+ // check 0
+ doit(S, "0.0", llvm::FloatStyle::Exponent, "0.000000e+00");
+ doit(S, "0.0", llvm::FloatStyle::ExponentUpper, "0.000000E+00");
+ doit(S, "0.0", llvm::FloatStyle::Fixed, "0.00");
+ doit(S, "0.0", llvm::FloatStyle::Percent, "0.00%");
+
+ // check that Exponent shifts left
+ doit(S, "0.5", llvm::FloatStyle::Exponent, "5.000000e-01");
+ doit(S, "0.5", llvm::FloatStyle::ExponentUpper, "5.000000E-01");
+ doit(S, "0.5", llvm::FloatStyle::Fixed, "0.50");
+ doit(S, "0.5", llvm::FloatStyle::Percent, "50.00%");
+
+ // check 1
+ doit(S, "1.0", llvm::FloatStyle::Exponent, "1.000000e+00");
+ doit(S, "1.0", llvm::FloatStyle::ExponentUpper, "1.000000E+00");
+ doit(S, "1.0", llvm::FloatStyle::Fixed, "1.00");
+ doit(S, "1.0", llvm::FloatStyle::Percent, "100.00%");
+
+ // check something with both an integer and a fraction
+ doit(S, "1.5", llvm::FloatStyle::Exponent, "1.500000e+00");
+ doit(S, "1.5", llvm::FloatStyle::ExponentUpper, "1.500000E+00");
+ doit(S, "1.5", llvm::FloatStyle::Fixed, "1.50");
+ doit(S, "1.5", llvm::FloatStyle::Percent, "150.00%");
+
+ // check negative
+ doit(S, "-1.5", llvm::FloatStyle::Exponent, "-1.500000e+00");
+ doit(S, "-1.5", llvm::FloatStyle::ExponentUpper, "-1.500000E+00");
+ doit(S, "-1.5", llvm::FloatStyle::Fixed, "-1.50");
+ doit(S, "-1.5", llvm::FloatStyle::Percent, "-150.00%");
+
+ // check rounding: 0
+ doit_precision(S, "0.0", llvm::FloatStyle::Exponent, 0, "0e+00");
+ doit_precision(S, "0.0", llvm::FloatStyle::ExponentUpper, 0, "0E+00");
+ doit_precision(S, "0.0", llvm::FloatStyle::Fixed, 0, "0");
+ doit_precision(S, "0.0", llvm::FloatStyle::Percent, 0, "0%");
+
+ // check round down
+ if (Precision >= 3) {
+ doit_precision(S, "1.25", llvm::FloatStyle::Exponent, 0, "1e+00");
+ doit_precision(S, "1.25", llvm::FloatStyle::ExponentUpper, 0, "1E+00");
+ doit_precision(S, "1.25", llvm::FloatStyle::Fixed, 0, "1");
+ doit_precision(S, "1.25", llvm::FloatStyle::Percent, 0, "125%");
+ }
+
+ // check round up
+ if (Precision >= 3) {
+ doit_precision(S, "1.25", llvm::FloatStyle::Exponent, 1, "1.3e+00");
+ doit_precision(S, "1.25", llvm::FloatStyle::ExponentUpper, 1, "1.3E+00");
+ doit_precision(S, "1.25", llvm::FloatStyle::Fixed, 1, "1.3");
+ doit_precision(S, "1.25", llvm::FloatStyle::Percent, 1, "125.0%");
+ }
+
+ // check round up to integer
+ if (Precision >= 3) {
+ doit_precision(S, "1.75", llvm::FloatStyle::Exponent, 0, "2e+00");
+ doit_precision(S, "1.75", llvm::FloatStyle::ExponentUpper, 0, "2E+00");
+ doit_precision(S, "1.75", llvm::FloatStyle::Fixed, 0, "2");
+ doit_precision(S, "1.75", llvm::FloatStyle::Percent, 0, "175%");
+ }
+
+ // check round up
+ if (Precision >= 3) {
+ doit_precision(S, "1.75", llvm::FloatStyle::Exponent, 1, "1.8e+00");
+ doit_precision(S, "1.75", llvm::FloatStyle::ExponentUpper, 1, "1.8E+00");
+ doit_precision(S, "1.75", llvm::FloatStyle::Fixed, 1, "1.8");
+ doit_precision(S, "1.75", llvm::FloatStyle::Percent, 1, "175.0%");
+ }
+
+ // check appending fewer than default number of zeros
+ if (Precision >= 3) {
+ doit_precision(S, "1.75", llvm::FloatStyle::Exponent, 3, "1.750e+00");
+ doit_precision(S, "1.75", llvm::FloatStyle::ExponentUpper, 3,
+ "1.750E+00");
+ doit_precision(S, "1.75", llvm::FloatStyle::Fixed, 3, "1.750");
+ doit_precision(S, "1.75", llvm::FloatStyle::Percent, 3, "175.000%");
+ }
+
+ // check appending more than default number of zeros
+ if (Precision >= 3) {
+ doit_precision(S, "1.75", llvm::FloatStyle::Exponent, 8,
+ "1.75000000e+00");
+ doit_precision(S, "1.75", llvm::FloatStyle::ExponentUpper, 8,
+ "1.75000000E+00");
+ doit_precision(S, "1.75", llvm::FloatStyle::Fixed, 8, "1.75000000");
+ doit_precision(S, "1.75", llvm::FloatStyle::Percent, 8, "175.00000000%");
+ }
+ }
+
+ // test the main types with wider ranges
+ auto sems = {llvm::APFloat::S_IEEEsingle, llvm::APFloat::S_IEEEdouble,
+ llvm::APFloat::S_IEEEquad, llvm::APFloat::S_PPCDoubleDouble,
+ llvm::APFloat::S_x87DoubleExtended};
----------------
arsenm wrote:
Check the exotic cases, like the new type without zero
https://github.com/llvm/llvm-project/pull/99088
More information about the llvm-commits
mailing list