将大价格值与SQLite数据库中的小数点一起存储在数据库中

时间:2018-01-11 07:03:30

标签: android database sqlite numbers decimal

可能我的问题很愚蠢,但我没有找到任何解决方案。 实际上,我想存储大价格金额,即

  

9999999999.99

在Sqlite数据库中并希望将其重新检索。我尝试使用TEXT,DOUBLE,REAL,LONG数据类型。

不幸的是,当我这样做时,它会返回不需要的值,即9.999999999 ..如果您有解决方案,请建议我,或指导我。

1 个答案:

答案 0 :(得分:0)

已定义的列类型相关性TEXTREALNUMERICVARCHARRUMPLESTILTSKIN是的,它可以),影响不大;例外情况是,如果类型是INTEGER PRIMARY KEYINTEGER PRIMARY KEY AUTOINCREMENT,在这种情况下,该列是SQLITE列 rowid 的别名,并且无法使用。 ROWIDs and the INTEGER PRIMARY KEY

基本上任何列(rowid除外)都可以按

存储任何类型的值
  

SQLite版本3数据库中的任何列,但INTEGER PRIMARY除外   KEY列,可用于存储任何存储类的值。   Datatypes In SQLite Version 3

该链接还说明了列类型如何转换为5种列类型之一: -

  • TEXT,
  • INTEGER,
  • REAL,
  • BLOB或
  • NUMERIC。

RuMpleStilskin(不区分大小写)将转换为NUMERIC,按照: -

  • (a)它不包含 INT (如果是这样的INTEGER亲和力)
  • (b)它不包含 TEXT CHAR CLOB (如果是TEXT亲和力,除非先前已处理过)
  • (c)它不包含 BLOB (如果是BLOB亲和力,除非事先处理)
  • (d)它不包含 REAL FLOA DOUB (如果是真实的亲和力,除非事先处理过)< / LI>
  • (e)如果以上都不是 NUMERIC &lt;&lt;&lt;&lt; Rumplestilskin来到这里。

最重要的是如何检索数据,尽管列的亲和力会影响数据的存储方式(存储类),如下所示: -

  

具有TEXT亲缘关系的列使用存储类存储所有数据   NULL,TEXT或BLOB。如果将数值数据插入到列中   TEXT亲缘关系在存储之前将其转换为文本形式。

     

具有NUMERIC亲和力的列可能包含使用全部五个值的值   存储类。当文本数据插入NUMERIC列时,   文本的存储类转换为INTEGER或REAL(按顺序)   (如果这种转换是无损且可逆的)。对于   SQLite认为,TEXT和REAL存储类之间的转换   如果前15个转换为无损且可逆转   保留该数字的有效十进制数字。如果   无法将TEXT无损转换为INTEGER或REAL   使用TEXT存储类存储该值。没有尝试   转换NULL或BLOB值。

     

字符串可能看起来像带有小数点的浮点字面值   和/或指数表示法,但只要该值可以表示为   一个整数,NUMERIC亲和力将其转换为整数。   因此,字符串&#39; 3.0e + 5&#39;存储在具有NUMERIC亲和力的列中   作为整数300000,而不是浮点值300000.0。

     

使用INTEGER关联的列与具有的列的行为相同   NUMERIC亲和力。 INTEGER和NUMERIC亲和力之间的区别   仅在CAST表达式中显而易见。

     

具有REAL亲和力的列的行为类似于具有NUMERIC的列   亲和力,除了它强制整数值进入浮点   表示。 (作为内部优化,小浮点   没有小数组件的值,并存储在REAL列中   亲和力以整数形式写入磁盘,以减少占用   空间并自动转换回浮点作为   读出的值。这种优化完全不可见   SQL级别,只能通过检查的原始位来检测   数据库文件。)

     

具有亲和力BLOB的列不喜欢一个存储类   另一个并没有尝试强制来自一个存储类的数据   进入另一个。   Datatypes In SQLite Version 3

对于浮点或双精度,您应使用Cursor方法getFloatgetDouble检索数据,然后相应地格式化结果(如果将其转换为字符串)。 注意!这假设双重或浮动的缺陷/精度损失无关紧要。 如果将值存储为字符串并且列亲缘关系为TEXT或BLOB,那么结果是无损的,并且可能是存储大数据的最佳方式(请参阅结果以确定什么是大数字)。

考虑使用列类型/亲和力 REAL TEXT INTEGER NUMERIC 定义5列的表格和 BLOB

按照: -

CREATE TABLE prices (
    _id INTEGER PRIMARY KEY, 
    PRICE1 REAL, 
    PRICE2 TEXT,
    PRICE3 INTEGER, 
    PRICE4 NUMERIC, 
    PRICE5 BLOB
)
  • ID列没有意义。

现在考虑这三种基本方法 - a)在所有5个PRICE中插入双倍值?列 - b)在所有5个PRICE中插入一个字符串值?列 - c)将所有行作为游标 : -

public void insertRowFromDouble(double price) {
    ContentValues cv = new ContentValues();
    cv.put(PRICES_PRICE1_COL,price);
    cv.put(PRICES_PRICE2_COL,price);
    cv.put(PRICES_PRICE3_COL,price);
    cv.put(PRICES_PRICE4_COl,price);
    cv.put(PRICES_PRICE5_COL,price);
    mDB.insert(TBNAME,null,cv);
}

public void insertRowFromString(String price) {
    ContentValues cv = new ContentValues();
    cv.put(PRICES_PRICE1_COL,price);
    cv.put(PRICES_PRICE2_COL,price);
    cv.put(PRICES_PRICE3_COL,price);
    cv.put(PRICES_PRICE4_COl,price);
    cv.put(PRICES_PRICE5_COL,price);
    mDB.insert(TBNAME,null,cv);
}

public Cursor getAllRows() {
    return mDB.query(TBNAME,null,null,null,null,null,null);
}

然后考虑以下代码: -

  • a)创建一个DecimalFormat
  • b)实例化Databasehelper
  • c)删除所有现有行(用于重新运行)
  • d)使用带有不同值的insertRowfromDouble方法插入5行,每行包含相同值的所有5列,即使它们各自具有不同的列类型。
  • e)与d)相同,但使用insertRowFromString方法并且在不同但接近的值内。
  • f)获取一个包含所有10行的游标。
  • g)使用根据getDouble然后DecimalFormat方法格式化的getString方法循环光标输出结果数据。

: -

    final DecimalFormat df = new DecimalFormat("#0.000000");
    mDBPricesHlpr = new PriceDBHelper(this);
    mDBPricesHlpr.getWritableDatabase().delete(PriceDBHelper.TBNAME,null,null);
    mDBPricesHlpr.insertRowFromDouble(999999999999999999999999999999999999999.99);
    mDBPricesHlpr.insertRowFromDouble(12345678901.123456);
    mDBPricesHlpr.insertRowFromDouble(9999999999.99);
    mDBPricesHlpr.insertRowFromDouble(0.01);
    mDBPricesHlpr.insertRowFromDouble(45678.45);
    mDBPricesHlpr.insertRowFromString("999999999999999999999999999999999999999999999999999999999999999999999999999.99");
    mDBPricesHlpr.insertRowFromString("12345678901.123456");
    mDBPricesHlpr.insertRowFromString("8888888888.88");
    mDBPricesHlpr.insertRowFromString("0.02");
    mDBPricesHlpr.insertRowFromString("56789.56");
    Cursor csr = mDBPricesHlpr.getAllRows();
    while (csr.moveToNext()) {
        Log.d("PRICEINFO_GETDBL"," Processing Row " + csr.getPosition() +
                "\n\tPRICE1=" + df.format(csr.getDouble(csr.getColumnIndex(PriceDBHelper.PRICES_PRICE1_COL))) +
                        "\n\tPRICE2=" + df.format(csr.getDouble(csr.getColumnIndex(PriceDBHelper.PRICES_PRICE2_COL))) +
                        "\n\tPRICE3=" + df.format(csr.getDouble(csr.getColumnIndex(PriceDBHelper.PRICES_PRICE3_COL))) +
                        "\n\tPRICE4=" + df.format(csr.getDouble(csr.getColumnIndex(PriceDBHelper.PRICES_PRICE4_COl))) +
                        "\n\tPRICE5=" + df.format(csr.getDouble(csr.getColumnIndex(PriceDBHelper.PRICES_PRICE5_COL)))
        );
        Log.d("PRICEINFO_GETSTR", " Processing Row " + csr.getPosition() +
                "\n\tPRICE1=" + csr.getString(csr.getColumnIndex(PriceDBHelper.PRICES_PRICE1_COL)) +
                        "\n\tPRICE2=" + csr.getString(csr.getColumnIndex(PriceDBHelper.PRICES_PRICE2_COL)) +
                        "\n\tPRICE3=" + csr.getString(csr.getColumnIndex(PriceDBHelper.PRICES_PRICE3_COL)) +
                        "\n\tPRICE4=" + csr.getString(csr.getColumnIndex(PriceDBHelper.PRICES_PRICE4_COl)) +
                        "\n\tPRICE5=" + csr.getString(csr.getColumnIndex(PriceDBHelper.PRICES_PRICE5_COL))
        );
    }

结果输出为: -

01-11 10:39:30.626 3680-3680/? D/PRICEINFO_GETDBL:  Processing Row 0
                                                    PRICE1=1000000000000000000000000000000000000000.000000
                                                    PRICE2=1000000000000000000000000000000000000000.000000
                                                    PRICE3=1000000000000000000000000000000000000000.000000
                                                    PRICE4=1000000000000000000000000000000000000000.000000
                                                    PRICE5=1000000000000000000000000000000000000000.000000
01-11 10:39:30.626 3680-3680/? D/PRICEINFO_GETSTR:  Processing Row 0
                                                    PRICE1=1e+39
                                                    PRICE2=1.0e+39
                                                    PRICE3=1e+39
                                                    PRICE4=1e+39
                                                    PRICE5=1e+39
01-11 10:39:30.626 3680-3680/? D/PRICEINFO_GETDBL:  Processing Row 1
                                                    PRICE1=12345678901.123500
                                                    PRICE2=12345678901.123500
                                                    PRICE3=12345678901.123500
                                                    PRICE4=12345678901.123500
                                                    PRICE5=12345678901.123500
01-11 10:39:30.626 3680-3680/? D/PRICEINFO_GETSTR:  Processing Row 1
                                                    PRICE1=1.23457e+10
                                                    PRICE2=12345678901.1235
                                                    PRICE3=1.23457e+10
                                                    PRICE4=1.23457e+10
                                                    PRICE5=1.23457e+10
01-11 10:39:30.626 3680-3680/? D/PRICEINFO_GETDBL:  Processing Row 2
                                                    PRICE1=9999999999.990000
                                                    PRICE2=9999999999.990000
                                                    PRICE3=9999999999.990000
                                                    PRICE4=9999999999.990000
                                                    PRICE5=9999999999.990000
01-11 10:39:30.626 3680-3680/? D/PRICEINFO_GETSTR:  Processing Row 2
                                                    PRICE1=1e+10
                                                    PRICE2=9999999999.99
                                                    PRICE3=1e+10
                                                    PRICE4=1e+10
                                                    PRICE5=1e+10
01-11 10:39:30.626 3680-3680/? D/PRICEINFO_GETDBL:  Processing Row 3
                                                    PRICE1=0.010000
                                                    PRICE2=0.010000
                                                    PRICE3=0.010000
                                                    PRICE4=0.010000
                                                    PRICE5=0.010000
01-11 10:39:30.630 3680-3680/? D/PRICEINFO_GETSTR:  Processing Row 3
                                                    PRICE1=0.01
                                                    PRICE2=0.01
                                                    PRICE3=0.01
                                                    PRICE4=0.01
                                                    PRICE5=0.01
01-11 10:39:30.630 3680-3680/? D/PRICEINFO_GETDBL:  Processing Row 4
                                                    PRICE1=45678.450000
                                                    PRICE2=45678.450000
                                                    PRICE3=45678.450000
                                                    PRICE4=45678.450000
                                                    PRICE5=45678.450000
01-11 10:39:30.630 3680-3680/? D/PRICEINFO_GETSTR:  Processing Row 4
                                                    PRICE1=45678.4
                                                    PRICE2=45678.45
                                                    PRICE3=45678.4
                                                    PRICE4=45678.4
                                                    PRICE5=45678.4
01-11 10:39:30.630 3680-3680/? D/PRICEINFO_GETDBL:  Processing Row 5
                                                    PRICE1=1000000000000000000000000000000000000000000000000000000000000000000000000000.000000
                                                    PRICE2=1000000000000000000000000000000000000000000000000000000000000000000000000000.000000
                                                    PRICE3=1000000000000000000000000000000000000000000000000000000000000000000000000000.000000
                                                    PRICE4=1000000000000000000000000000000000000000000000000000000000000000000000000000.000000
                                                    PRICE5=1000000000000000000000000000000000000000000000000000000000000000000000000000.000000
01-11 10:39:30.630 3680-3680/? D/PRICEINFO_GETSTR:  Processing Row 5
                                                    PRICE1=1e+75
                                                    PRICE2=999999999999999999999999999999999999999999999999999999999999999999999999999.99
                                                    PRICE3=1e+75
                                                    PRICE4=1e+75
                                                    PRICE5=999999999999999999999999999999999999999999999999999999999999999999999999999.99
01-11 10:39:30.630 3680-3680/? D/PRICEINFO_GETDBL:  Processing Row 6
                                                    PRICE1=12345678901.123500
                                                    PRICE2=12345678901.123500
                                                    PRICE3=12345678901.123500
                                                    PRICE4=12345678901.123500
                                                    PRICE5=12345678901.123500
01-11 10:39:30.630 3680-3680/? D/PRICEINFO_GETSTR:  Processing Row 6
                                                    PRICE1=1.23457e+10
                                                    PRICE2=12345678901.123456
                                                    PRICE3=1.23457e+10
                                                    PRICE4=1.23457e+10
                                                    PRICE5=12345678901.123456
01-11 10:39:30.630 3680-3680/? D/PRICEINFO_GETDBL:  Processing Row 7
                                                    PRICE1=8888888888.880000
                                                    PRICE2=8888888888.880000
                                                    PRICE3=8888888888.880000
                                                    PRICE4=8888888888.880000
                                                    PRICE5=8888888888.880000
01-11 10:39:30.630 3680-3680/? D/PRICEINFO_GETSTR:  Processing Row 7
                                                    PRICE1=8.88889e+09
                                                    PRICE2=8888888888.88
                                                    PRICE3=8.88889e+09
                                                    PRICE4=8.88889e+09
                                                    PRICE5=8888888888.88
01-11 10:39:30.630 3680-3680/? D/PRICEINFO_GETDBL:  Processing Row 8
                                                    PRICE1=0.020000
                                                    PRICE2=0.020000
                                                    PRICE3=0.020000
                                                    PRICE4=0.020000
                                                    PRICE5=0.020000
01-11 10:39:30.634 3680-3680/? D/PRICEINFO_GETSTR:  Processing Row 8
                                                    PRICE1=0.02
                                                    PRICE2=0.02
                                                    PRICE3=0.02
                                                    PRICE4=0.02
                                                    PRICE5=0.02
01-11 10:39:30.634 3680-3680/? D/PRICEINFO_GETDBL:  Processing Row 9
                                                    PRICE1=56789.560000
                                                    PRICE2=56789.560000
                                                    PRICE3=56789.560000
                                                    PRICE4=56789.560000
                                                    PRICE5=56789.560000
01-11 10:39:30.634 3680-3680/? D/PRICEINFO_GETSTR:  Processing Row 9
                                                    PRICE1=56789.6
                                                    PRICE2=56789.56
                                                    PRICE3=56789.6
                                                    PRICE4=56789.6
                                                    PRICE5=56789.56

所以: -

  • 对于使用getDouble的第0行(通过double存储的9999999999999999999999999999999999999999999.99),列类型无关紧要,但对于getString,当列类型为TEXT时存在细微差别。但是,精确度会失去价值(请参阅上面的警告)。

  • 对于第1行(通过double存储的12345678901.123500),getDouble适用于15位有效数字。使用getString,除了TEXT列之外,其他所有内容都因精度损失而丢失。

  • 对于第2行(通过double存储的9999999999.99)与第1行的结果非常相似。

  • 对于第3行(通过double存储0.01)很好。

  • 对于第4行(通过double存储45678.45),精确丢失是getString的一个问题,除非它是TEXT列。

  • 对于第5-9行,数据通过字符串存储,TEXT和BLOB列在所有情况下都准确地存储值,没有精度损失。否则结果是相似的。