使用精确数学时,尽可能使用给定的精确数值。例如,在比较中使用的数字会按给定的值精确使用,不会改变数值。在严格 SQL 模式下,对于具有精确数据类型(DECIMAL 或整数)的列进行 INSERT 操作时,如果数字在列的范围内,则会以其精确值插入。检索时,值应与插入时相同。(如果未启用严格 SQL 模式,则允许对 INSERT 进行截断。)With precision math, exact-value numbers are used as given
whenever possible. For example, numbers in comparisons are used
exactly as given without a change in value. In strict SQL mode,
for INSERT into a column with an
exact data type (DECIMAL or
integer), a number is inserted with its exact value if it is
within the column range. When retrieved, the value should be the
same as what was inserted. (If strict SQL mode is not enabled,
truncation for INSERT is
permissible.)
数值表达式的处理取决于表达式包含的值类型:Handling of a numeric expression depends on what kind of values the expression contains:
如果存在任何近似值,该表达式就是近似的,并使用浮点运算进行求值。If any approximate values are present, the expression is approximate and is evaluated using floating-point arithmetic.
如果没有近似值存在,则表达式仅包含精确值。如果任何精确值包含小数部分(小数点后的数值),则该表达式使用
DECIMAL精确算术进行计算,并且精度为 65 位。术语 “精确” 受制于二进制可表示范围的限制。例如,1.0/3.0可以在十进制表示中近似为.333...,但不能写成精确数,因此(1.0/3.0)*3.0不会精确计算为1.0。If no approximate values are present, the expression contains only exact values. If any exact value contains a fractional part (a value following the decimal point), the expression is evaluated usingDECIMALexact arithmetic and has a precision of 65 digits. The term “exact” is subject to the limits of what can be represented in binary. For example,1.0/3.0can be approximated in decimal notation as.333..., but not written as an exact number, so(1.0/3.0)*3.0does not evaluate to exactly1.0.否则,该表达式仅包含整数值。该表达式是精确的,使用整数算术进行计算,并且具有与
BIGINT(64 位)相同的精度。Otherwise, the expression contains only integer values. The expression is exact and is evaluated using integer arithmetic and has a precision the same asBIGINT(64 bits).
如果数值表达式包含任何字符串,它们会被转换为双精度浮点值,并且该表达式是近似的。If a numeric expression contains any strings, they are converted to double-precision floating-point values and the expression is approximate.
插入到数字列受 SQL 模式的影响,该模式由 sql_mode 系统变量控制。(参见 第 7.1.11 节,“服务器 SQL 模式”。)以下讨论提到严格模式(由 STRICT_ALL_TABLES 或 STRICT_TRANS_TABLES 模式值选择)以及 ERROR_FOR_DIVISION_BY_ZERO。要启用所有限制,您可以简单使用 TRADITIONAL 模式,其中包括严格模式值和 ERROR_FOR_DIVISION_BY_ZERO:Inserts into numeric columns are affected by the SQL mode, which
is controlled by the sql_mode
system variable. (See Section 7.1.11, “Server SQL Modes”.) The following
discussion mentions strict mode (selected by the
STRICT_ALL_TABLES or
STRICT_TRANS_TABLES mode values)
and ERROR_FOR_DIVISION_BY_ZERO.
To turn on all restrictions, you can simply use
TRADITIONAL mode, which includes
both strict mode values and
ERROR_FOR_DIVISION_BY_ZERO:
SET sql_mode='TRADITIONAL';
如果一个数字被插入到精确类型列(DECIMAL 或整数)中,并且该数字在列的范围和精度之内,则会以其精确值插入。If a number is inserted into an exact type column
(DECIMAL or integer), it is
inserted with its exact value if it is within the column range and
precision.
如果数值的小数部分位数过多,则会进行四舍五入,并生成一条通知。四舍五入的方法如 第 14.24.4 节,“四舍五入行为” 中所述。即使在严格模式下,由于小数部分四舍五入而导致的截断也不算错误。If the value has too many digits in the fractional part, rounding occurs and a note is generated. Rounding is done as described in Section 14.24.4, “Rounding Behavior”. Truncation due to rounding of the fractional part is not an error, even in strict mode.
如果值的整数部分位数过多,则值过大(超出范围),处理方式如下:If the value has too many digits in the integer part, it is too large (out of range) and is handled as follows:
如果未启用严格模式,值将截断为最接近的合法值,并生成警告。If strict mode is not enabled, the value is truncated to the nearest legal value and a warning is generated.
如果启用严格模式,则会发生溢出错误。If strict mode is enabled, an overflow error occurs.
下溢不会被检测,因此下溢处理未定义。Underflow is not detected, so underflow handling is undefined.
对于将字符串插入数值列,如果字符串包含非数字内容,则字符串到数字的转换处理如下:For inserts of strings into numeric columns, conversion from string to number is handled as follows if the string has nonnumeric contents:
以非数字开头的字符串不能作为数字使用,在严格模式下会产生错误,否则会发出警告。这包括空字符串。A string that does not begin with a number cannot be used as a number and produces an error in strict mode, or a warning otherwise. This includes the empty string.
以数字开头的字符串可以被转换,但非数字尾部会被截断。如果截断部分包含除空格之外的内容,在严格模式下会产生错误,否则会发出警告。A string that begins with a number can be converted, but the trailing nonnumeric portion is truncated. If the truncated portion contains anything other than spaces, this produces an error in strict mode, or a warning otherwise.
默认情况下,除以零会产生 NULL 结果且不会有警告。通过适当设置 SQL 模式,可以限制除以零的操作。By default, division by zero produces a result of
NULL and no warning. By setting the SQL mode
appropriately, division by zero can be restricted.
启用 ERROR_FOR_DIVISION_BY_ZERO SQL 模式时,MySQL 对除以零的处理方式会有所不同:With the
ERROR_FOR_DIVISION_BY_ZERO SQL
mode enabled, MySQL handles division by zero differently:
如果未启用严格模式,会出现警告。If strict mode is not enabled, a warning occurs.
如果启用了严格模式,则禁止涉及除以零的插入和更新操作,并会出现错误。If strict mode is enabled, inserts and updates involving division by zero are prohibited, and an error occurs.
换句话说,涉及执行除以零运算的表达式的插入和更新可以被视为错误,但这需要除了严格模式之外,还需要ERROR_FOR_DIVISION_BY_ZERO。In other words, inserts and updates involving expressions that
perform division by zero can be treated as errors, but this
requires
ERROR_FOR_DIVISION_BY_ZERO in
addition to strict mode.
假设我们有以下语句:Suppose that we have this statement:
INSERT INTO t SET i = 1/0;
这是严格模式和 ERROR_FOR_DIVISION_BY_ZERO 模式组合时的情况。This is what happens for combinations of strict and
ERROR_FOR_DIVISION_BY_ZERO
modes.
sql_mode 值sql_mode Value |
结果Result |
|---|---|
''(默认)'' (Default) |
没有警告,也没有错误;i 被设置为 NULL。No warning, no error; i is set to
NULL. |
| 严格strict | 没有警告,也没有错误;i 被设置为 NULL。No warning, no error; i is set to
NULL. |
ERROR_FOR_DIVISION_BY_ZERO |
警告,没有错误;i 被设置为 NULL。Warning, no error; i is set to
NULL. |
严格,ERROR_FOR_DIVISION_BY_ZEROstrict,ERROR_FOR_DIVISION_BY_ZERO |
错误状态;没有插入行。Error condition; no row is inserted. |