00001 // 00002 // Copyright 2017 The Abseil Authors. 00003 // 00004 // Licensed under the Apache License, Version 2.0 (the "License"); 00005 // you may not use this file except in compliance with the License. 00006 // You may obtain a copy of the License at 00007 // 00008 // https://www.apache.org/licenses/LICENSE-2.0 00009 // 00010 // Unless required by applicable law or agreed to in writing, software 00011 // distributed under the License is distributed on an "AS IS" BASIS, 00012 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00013 // See the License for the specific language governing permissions and 00014 // limitations under the License. 00015 // 00016 // ----------------------------------------------------------------------------- 00017 // File: numbers.h 00018 // ----------------------------------------------------------------------------- 00019 // 00020 // This package contains functions for converting strings to numbers. For 00021 // converting numbers to strings, use `StrCat()` or `StrAppend()` in str_cat.h, 00022 // which automatically detect and convert most number values appropriately. 00023 00024 #ifndef ABSL_STRINGS_NUMBERS_H_ 00025 #define ABSL_STRINGS_NUMBERS_H_ 00026 00027 #include <cstddef> 00028 #include <cstdlib> 00029 #include <cstring> 00030 #include <ctime> 00031 #include <limits> 00032 #include <string> 00033 #include <type_traits> 00034 00035 #include "absl/base/macros.h" 00036 #include "absl/base/port.h" 00037 #include "absl/numeric/int128.h" 00038 #include "absl/strings/string_view.h" 00039 00040 namespace absl { 00041 00042 // SimpleAtoi() 00043 // 00044 // Converts the given string into an integer value, returning `true` if 00045 // successful. The string must reflect a base-10 integer (optionally followed or 00046 // preceded by ASCII whitespace) whose value falls within the range of the 00047 // integer type. If any errors are encountered, this function returns `false`, 00048 // leaving `out` in an unspecified state. 00049 template <typename int_type> 00050 ABSL_MUST_USE_RESULT bool SimpleAtoi(absl::string_view s, int_type* out); 00051 00052 // SimpleAtof() 00053 // 00054 // Converts the given string (optionally followed or preceded by ASCII 00055 // whitespace) into a float, which may be rounded on overflow or underflow. 00056 // See https://en.cppreference.com/w/c/string/byte/strtof for details about the 00057 // allowed formats for `str`. If any errors are encountered, this function 00058 // returns `false`, leaving `out` in an unspecified state. 00059 ABSL_MUST_USE_RESULT bool SimpleAtof(absl::string_view str, float* out); 00060 00061 // SimpleAtod() 00062 // 00063 // Converts the given string (optionally followed or preceded by ASCII 00064 // whitespace) into a double, which may be rounded on overflow or underflow. 00065 // See https://en.cppreference.com/w/c/string/byte/strtof for details about the 00066 // allowed formats for `str`. If any errors are encountered, this function 00067 // returns `false`, leaving `out` in an unspecified state. 00068 ABSL_MUST_USE_RESULT bool SimpleAtod(absl::string_view str, double* out); 00069 00070 // SimpleAtob() 00071 // 00072 // Converts the given string into a boolean, returning `true` if successful. 00073 // The following case-insensitive strings are interpreted as boolean `true`: 00074 // "true", "t", "yes", "y", "1". The following case-insensitive strings 00075 // are interpreted as boolean `false`: "false", "f", "no", "n", "0". If any 00076 // errors are encountered, this function returns `false`, leaving `out` in an 00077 // unspecified state. 00078 ABSL_MUST_USE_RESULT bool SimpleAtob(absl::string_view str, bool* out); 00079 00080 } // namespace absl 00081 00082 // End of public API. Implementation details follow. 00083 00084 namespace absl { 00085 namespace numbers_internal { 00086 00087 // safe_strto?() functions for implementing SimpleAtoi() 00088 bool safe_strto32_base(absl::string_view text, int32_t* value, int base); 00089 bool safe_strto64_base(absl::string_view text, int64_t* value, int base); 00090 bool safe_strtou32_base(absl::string_view text, uint32_t* value, int base); 00091 bool safe_strtou64_base(absl::string_view text, uint64_t* value, int base); 00092 00093 static const int kFastToBufferSize = 32; 00094 static const int kSixDigitsToBufferSize = 16; 00095 00096 // Helper function for fast formatting of floating-point values. 00097 // The result is the same as printf's "%g", a.k.a. "%.6g"; that is, six 00098 // significant digits are returned, trailing zeros are removed, and numbers 00099 // outside the range 0.0001-999999 are output using scientific notation 00100 // (1.23456e+06). This routine is heavily optimized. 00101 // Required buffer size is `kSixDigitsToBufferSize`. 00102 size_t SixDigitsToBuffer(double d, char* buffer); 00103 00104 // These functions are intended for speed. All functions take an output buffer 00105 // as an argument and return a pointer to the last byte they wrote, which is the 00106 // terminating '\0'. At most `kFastToBufferSize` bytes are written. 00107 char* FastIntToBuffer(int32_t, char*); 00108 char* FastIntToBuffer(uint32_t, char*); 00109 char* FastIntToBuffer(int64_t, char*); 00110 char* FastIntToBuffer(uint64_t, char*); 00111 00112 // For enums and integer types that are not an exact match for the types above, 00113 // use templates to call the appropriate one of the four overloads above. 00114 template <typename int_type> 00115 char* FastIntToBuffer(int_type i, char* buffer) { 00116 static_assert(sizeof(i) <= 64 / 8, 00117 "FastIntToBuffer works only with 64-bit-or-less integers."); 00118 // TODO(jorg): This signed-ness check is used because it works correctly 00119 // with enums, and it also serves to check that int_type is not a pointer. 00120 // If one day something like std::is_signed<enum E> works, switch to it. 00121 if (static_cast<int_type>(1) - 2 < 0) { // Signed 00122 if (sizeof(i) > 32 / 8) { // 33-bit to 64-bit 00123 return FastIntToBuffer(static_cast<int64_t>(i), buffer); 00124 } else { // 32-bit or less 00125 return FastIntToBuffer(static_cast<int32_t>(i), buffer); 00126 } 00127 } else { // Unsigned 00128 if (sizeof(i) > 32 / 8) { // 33-bit to 64-bit 00129 return FastIntToBuffer(static_cast<uint64_t>(i), buffer); 00130 } else { // 32-bit or less 00131 return FastIntToBuffer(static_cast<uint32_t>(i), buffer); 00132 } 00133 } 00134 } 00135 00136 // Implementation of SimpleAtoi, generalized to support arbitrary base (used 00137 // with base different from 10 elsewhere in Abseil implementation). 00138 template <typename int_type> 00139 ABSL_MUST_USE_RESULT bool safe_strtoi_base(absl::string_view s, int_type* out, 00140 int base) { 00141 static_assert(sizeof(*out) == 4 || sizeof(*out) == 8, 00142 "SimpleAtoi works only with 32-bit or 64-bit integers."); 00143 static_assert(!std::is_floating_point<int_type>::value, 00144 "Use SimpleAtof or SimpleAtod instead."); 00145 bool parsed; 00146 // TODO(jorg): This signed-ness check is used because it works correctly 00147 // with enums, and it also serves to check that int_type is not a pointer. 00148 // If one day something like std::is_signed<enum E> works, switch to it. 00149 if (static_cast<int_type>(1) - 2 < 0) { // Signed 00150 if (sizeof(*out) == 64 / 8) { // 64-bit 00151 int64_t val; 00152 parsed = numbers_internal::safe_strto64_base(s, &val, base); 00153 *out = static_cast<int_type>(val); 00154 } else { // 32-bit 00155 int32_t val; 00156 parsed = numbers_internal::safe_strto32_base(s, &val, base); 00157 *out = static_cast<int_type>(val); 00158 } 00159 } else { // Unsigned 00160 if (sizeof(*out) == 64 / 8) { // 64-bit 00161 uint64_t val; 00162 parsed = numbers_internal::safe_strtou64_base(s, &val, base); 00163 *out = static_cast<int_type>(val); 00164 } else { // 32-bit 00165 uint32_t val; 00166 parsed = numbers_internal::safe_strtou32_base(s, &val, base); 00167 *out = static_cast<int_type>(val); 00168 } 00169 } 00170 return parsed; 00171 } 00172 00173 } // namespace numbers_internal 00174 00175 // SimpleAtoi() 00176 // 00177 // Converts a string to an integer, using `safe_strto?()` functions for actual 00178 // parsing, returning `true` if successful. The `safe_strto?()` functions apply 00179 // strict checking; the string must be a base-10 integer, optionally followed or 00180 // preceded by ASCII whitespace, with a value in the range of the corresponding 00181 // integer type. 00182 template <typename int_type> 00183 ABSL_MUST_USE_RESULT bool SimpleAtoi(absl::string_view s, int_type* out) { 00184 return numbers_internal::safe_strtoi_base(s, out, 10); 00185 } 00186 00187 } // namespace absl 00188 00189 #endif // ABSL_STRINGS_NUMBERS_H_