2017-12-08 10 views
0

DBからScientific数を取得するためにREST EndpointをテストするPythonコードを作成しており、正しいJSON科学数値形式でデータベースから科学フォーマットが返されることを検証します。PythonのJSONへのDB出力からの換算

私は、いくつかの科学的数字が変換されているという問題があります。たとえば、JSONローダーはeを大文字に変換し、一部の値は整数に変換します。ここにいくつかのコード例があります。あなたがDBのバックエンドを持っていないので、コードは私がやっていることを正確に行っていません。

import json 
import decimal 

class DecimalEncoder(json.JSONEncoder): 
    def default(self, o): 
    if isinstance(o, decimal.Decimal): 
     print 'In here: ' + str(o) 
     return str(o) 
    return super(DecimalEncoder, self).default(o) 

class JSONUtils: 
    def __init__(self, response): 
     self.response = response 
     self.jsonData = None 
     self.LoadData() 

    # print 'jsonData: ' + json.dumps(self.jsonData, cls=DecimalEncoder, indent=2) 

    def GetData(self): 
     return self.jsonData   

    def GetAsStr(self): 
     return json.dumps(self.GetData(), cls=DecimalEncoder) 

    def LoadData (self): 
     if (self.jsonData == None): 
      if (type(self.response) == str or type(self.response) == unicode): 
       print '****type1' 
       self.jsonData = json.loads(self.response, parse_float=decimal.Decimal) 
      elif (type(self.response) == dict): 
       print '****type2' 
       dump = json.dumps(self.response, cls=DecimalEncoder) 
       self.jsonData = json.loads(dump, parse_float=decimal.Decimal) 

    def GetJSONChunk(self, path): 
     returnValue = '' 
     curPath  = '' 
     try: 
      if (type(path) == str): 
       returnValue = self.jsonData[path] 
      elif (type(path) == list): 
       temp = '' 
       firstTime = True 
       for curPath in path: 
        if firstTime == True: 
         temp = self.jsonData[curPath] 
         firstTime = False 
        else: 
         temp = temp[curPath] 
       returnValue = temp 
      else: 
       print 'Unknown type in GetJSONChunk: ' + unicode(type(path)) 
     except KeyError as err: 
      ti.DBG_OUT('JSON chunk doesn\'t have value: ' + unicode(path)) 
      returnValue = self.kNoNode 
     except IndexError as err: 
      ti.DBG_OUT('Index does not exist: ' + unicode(curPath)) 
      returnValue = self.kInvalidIndex 

     return returnValue 

info = { "fldName":1.47e-10 } # converts to 1.47e-10 (e to E) 
# info = { "fldName":1.47e10 } # convers to 14700000000.0 
# info = { "fldName":1.47e+10 } # convers to 14700000000.0 
# info = { "fldName":1.47E+10 } # convers to 14700000000.0 
# info = { "fldName":123456789} # example shows larger # support 
print 'info: ' + str (info) 
myJSON = JSONUtils(info) 
print 'type: ' + str(myJSON.jsonData) 
print 'myJSON: ' + myJSON.GetAsStr() 
value = myJSON.GetJSONChunk ('fldName') 
print 'Type: ' + str(type(value)) 
print value 

DBの結果と期待値を比較する必要があります。唯一の科学的数字を特定する方法はありますか?小数点以下の値を2倍して文字列として返しません。ご覧のとおり、私はすでに、バックエンドデータベースの基準/機能を確実に満たすために返されているDoublesを保護しようとしています。小数点以下20桁以上の数字を入力します。

実際の結果は、#infoで始まる各コード行で示されます。

答えて

0

私はあなたの質問に完全にはっきりしていないので、これが基本的な方法でない場合は教えてください。

私は、Python の表示方法と数字の実際の値との間に何らかの混乱があるかもしれないと思います。

例えば、私のように数千を書き込むことができます。

>>> 1000 
1000.0 
>>> 1E3 
1000.0 
>>> 10E2 
1000.0 
>>> 1e3 
1000.0 
>>> 1e+3 
1000.0 

これらはすべて異なる表現数のですが、それらはすべて数値的に等価です。 JSONも同様に柔軟性があります。上記の表現はすべてJSONでも有効です。

10000000000000000000000000000.0 

をしかしprint文はとして表示されます:

同様に、私は書くことができます

1e+28 

しかし、それはまだ同じ番号です。それは決して「変換」されていません。あなたの番号が>= 1E16になると、PythonはE記法を使用します。

私はこのようになりますJSON受けるのであれば:

{ 
    "val1": 1e+3, 
    "val2": 1e+20 
} 

次の出力:

values = json.loads('{"val1": 1e+3, "val2": 1e+20}') 
for k, v in values.items(): 
    print(k, '=', v) 

は次のようになります。

val1 = 1000.0 
val2 = 1e+20 
+0

私はあなたのように数字を表現することができます知っています整数または同じ番号を科学的表記法で使用します。私は、データベースから返された科学的な値をテストし、それらの精度をチェックしています。 IOW:データベースは、番号/科学番号を正しく表していますか?私はとにかく値が混乱しないようにしたい。起こっていることは、データベースが有効な科学値を返し、JSONのロードを実行すると値が変換されることになります。はい...有効な科学的表現にはなりましたが、私は原価を必要としません。どんなアイデアでも大歓迎です。 – Keith

関連する問題