如何最好地表示SQL Server中的有理数?

时间:2009-12-19 18:48:09

标签: sql sql-server rational-numbers

我正在使用原生作为有理数提供的数据。我在C#中有一个光滑的generic C# class which beautifully represents this data,允许转换为许多其他形式。不幸的是,当我转身并希望将其存储在SQL中时,我想到了几个解决方案,但没有一个非常令人满意。

这是一个例子。我有原始值2/3,我的new Rational<int>(2, 3)可以在C#中轻松处理。我想到的将其存储在数据库中的选项如下:

  1. 就像十进制/浮点一样,即各种精度和精确度的值= 0.66666667优点:这允许我查询数据,例如找到值&lt; 1。 缺点:它失去了准确性,当我在UI中显示这个简单的值时它很难看。

  2. 存储为两个完全整数字段,例如numerator = 2,分母= 3各种精确度和精确度。 优点:这使我能够精确地表示原始值,并在以后以最简单的形式显示它。 缺点:我现在有两个字段来表示这个值,现在查询很复杂/效率低,因为每个查询都必须执行算术,例如find numerator / denominator&lt; 1。

  3. 序列化为字符串数据,即"2/3"。我将能够知道最大字符串长度并且有一个varchar可以容纳这个。 优点:我回到了一个领域,但有一个确切的代表。 缺点:查询几乎被破坏并支付序列化费用。

  4. #1&amp;的组合#2。 优点:轻松/高效地查询值范围,在UI中具有精确值。 缺点: 三个字段(!?!)来保存一个数据,必须保持多个同步表示,这会破坏D.R.Y。

  5. #1&amp;的组合#3。 优点:轻松/高效地查询值范围,在UI中具有精确值。 缺点:返回两个字段以保存一个数据,必须保持多个表示同步,这会破坏D.R.Y.,并且必须支付额外的序列化费用。

  6. 有没有人有另一种开箱即用的解决方案比这些更好?还有其他我不考虑的事情吗?有没有一种相对简单的方法在SQL中做到这一点,我只是不知道?

5 个答案:

答案 0 :(得分:7)

如果您使用的是SQL Server 2005或2008,则可以选择define your own CLR data types

  

从SQL Server 2005开始,你   可以使用用户定义的类型(UDT)   扩展标量类型系统   服务器,启用CLR存储   SQL Server数据库中的对象。的UDT   可以包含多个元素   有行为,区分他们   来自传统的别名数据类型   它由一个SQL Server组成   系统数据类型。

     

因为UDT是由访问的   系统作为一个整体,它们的用途   复杂的数据类型可能是负面的   影响表现。复杂的数据是   通常使用最好的模型   传统的行和表。 UDT in   SQL Server非常适合   以下内容:

     
      
  • 日期,时间,货币和扩展数字类型
  •   
  • 地理空间应用
  •   
  • 编码或加密数据
  •   

如果你能忍受这些限制,我无法想象一种更好的方法来映射你已经在自定义类中捕获的数据。

答案 1 :(得分:6)

我可能会使用选项#4,但是使用第3列的计算列来避免同步/干扰问题(也意味着您实际上只存储了2列,避免了“三个字段”问题)。

在SQL server中,计算列的定义如下:

CREATE TABLE dbo.Whatever(
   Numerator INT NOT NULL,
   Denominator INT NOT NULL,
   Value AS (Numerator / Denominator) PERSISTED
)

(注意你可能需要做一些类型转换和验证Denominator不为零等)。

此外,SQL 2005添加了一个PERSISTED计算列,可以在查询时删除计算。

答案 2 :(得分:2)

您需要多少精度?

语言C#或其他语言将在精度的给定位置舍入2 / 3rds。如果您正在使用的任何内容都可以使用10的科学记数法的十进制值,那么在db中相应地设置精度。

如果确实需要精确度,那么将分子和分子分开。分母。这将确保您始终可以访问所需的任何精度,并且可以使用computed column来表示快速过滤的值:

numerator INT,
denominator INT,
result AS CASE WHEN denominator > 0 THEN numerator / denominator ELSE NULL END

答案 3 :(得分:0)

我已经尝试使用SQL Server 2008中的geometry data type来存储和操作有理数。基本上,我假设分子进入X槽,分母进入虚构几何点的Y槽。

这对我的需求有好处,但对你来说可能毫无用处。这取决于您的优先级(性能,代码可读性等)。我个人发现用于几何数据操作的T-SQL很难编写和读取。

答案 4 :(得分:0)

你看多少精确度? double / float提供了不错的精度(在我看来)。我相信科学/天文数据需要更高的精度。我知道像matlab和mathematica这样的库很擅长这些。我发现你可以在你的.net程序中使用mathematica。 Here is the link

修改:添加更多链接和引号

“当Mathematica对有理数进行操作时,无论需要多少位数,它都会给出一个精确的结果”来自here

Another good read,但你必须实现它我想