想要将 MySQL 字段的值限制在特定范围内(十进制值)
Posted
技术标签:
【中文标题】想要将 MySQL 字段的值限制在特定范围内(十进制值)【英文标题】:Want to restrict the value of a MySQL field to specific range (Decimal values) 【发布时间】:2012-03-23 10:53:08 【问题描述】:我想将表格行中字段的值限制在特定范围内。是否可以将我的 relationship_level 字段限制为 [0.00 到 1.00]?
目前我使用 DECIMAL(2,2),它不允许 DECIMAL(1,2),因为 M 必须 >= D。我假设 DECIMAL(2,2) 的数据类型实际上允许值从 00.00 到 99.99?
CREATE TABLE relationships (
from_user_id MEDIUMINT UNSIGNED NOT NULL,
to_user_id MEDIUMINT UNSIGNED NOT NULL,
relationship_level DECIMAL(2,2) UNSIGNED NOT NULL,
PRIMARY KEY (from_user_id, to_user_id),
FOREIGN KEY (from_user_id) REFERENCES users (user_id) ON DELETE CASCADE ON UPDATE NO ACTION,
FOREIGN KEY (to_user_id) REFERENCES users (user_id) ON DELETE CASCADE ON UPDATE NO ACTION,
INDEX relationship_from_to (to_user_id, from_user_id, relationship_level)
) ENGINE = INNODB;
有没有更好的方法来做到这一点,谁能预见任何限制?
非常感谢!
【问题讨论】:
如果您真的想将值从0.00
限制为1.00
,您应该使用DECIMAL(3,2)
数据类型和引用“稳定”(引用)表的FK,只有101行。就像您的其他问题的答案一样:Limit the value of a mysql datatype to a specific range
完美。我想它会涉及到与此类似的东西(FK 引用另一个限制范围的表)我只是想知道是否存在比以前的方法更“有效”的方法。非常感谢。
还有另一种可能性,但我没有使用它,所以我不知道有任何问题。使用WITH CHECK OPTION
定义可更新视图。但是,您必须只使用该视图而不是表(至少对于插入和更新):CREATE VIEW Syntax
【参考方案1】:
实际上,DECIMAL(2,2)
将允许最多 2 位小数,这两个都分配到小数位。该字段的最大值为0.99
,最小值为0.00
。
要将值限制为 00.00
到 99.99
,请使用 DECIMAL(4,2) UNSIGNED
。
【讨论】:
好的,感谢您阐明使用 DECIMAL(2,2)=[0.00 到 0.99] 实际得到的范围。实际上是否有可能以这种方式限制它以达到 [0.00 到 1.00] 的范围,我假设它会涉及 DECIMAL 数据类型的替代方案。 不,您不能从[0.00 to 1.00]
受到限制。使用DECIMAL(3,2) UNSIGNED
,您可以拥有从 0.00 到 9.99
您可以使用 BEFORE INSERT/UPDATE TRIGGERS 来限制它。您可以通过在触发器中将 NOT NULL 列设置为 NULL 来强制这些值或触发错误。【参考方案2】:
您可以在 MySQL 中使用触发器模拟检查约束。
例如,如果您想强制将所有大于 1.00 的值存储为 1.00,您可以使用 2 个触发器来执行此操作,如下所示:
DELIMITER $$
DROP TRIGGER IF EXISTS tr_b_ins_relationships $$
CREATE TRIGGER tr_b_ins_relationships BEFORE INSERT ON relationships FOR EACH ROW BEGIN
IF new.relationship_level > 1
THEN
SET new.relationship_level = 1;
END IF;
END $$
DELIMITER ;
DELIMITER $$
DROP TRIGGER IF EXISTS tr_b_upd_relationships $$
CREATE TRIGGER tr_b_upd_relationships BEFORE UPDATE ON relationships FOR EACH ROW BEGIN
IF new.relationship_level > 1
THEN
SET new.relationship_level = 1;
END IF;
END $$
DELIMITER ;
【讨论】:
触发器听起来很棒,我想我会用它们来解决这个问题,现在还有其他一些地方。谢谢! 苹果对亚当来说听起来也很棒(而且看起来很好吃)。 Are database triggers evil? 我断言这是对触发器的合理使用,特别是考虑到 MySQL 不支持检查约束这一事实。以上是关于想要将 MySQL 字段的值限制在特定范围内(十进制值)的主要内容,如果未能解决你的问题,请参考以下文章