如何在 Flutter Dart 中迭代 JSON Map 并检索键值结果?

Posted

技术标签:

【中文标题】如何在 Flutter Dart 中迭代 JSON Map 并检索键值结果?【英文标题】:How do I iterate JSON Map and retrieve key-value results in flutter Dart? 【发布时间】:2019-07-05 05:12:41 【问题描述】:

我正在 Flutter dart 中处理 json。

    final response = http.get('url'). 
response.body returns this json String format: String stringJson = "symbols_returned":147,"base":"USD","data":"AED":"3.672940","AFN":"75.617000","ALL":"109.780000","AMD":"490.740000","ANG":"1.797350","AOA":"313.147500","ARS":"37.864500","AUD":"1.408450","AWG":"1.800000","AZN":"1.702500","BAM":"1.727050","BBD":"2.004250","BCH":"0.008196","BDT":"83.950500","BGN":"1.726900","BHD":"0.377470","BIF":"1800.000000","BMD":"1.000000","BND":"1.357650","BOB":"6.919100","BRL":"3.729400","BSD":"1.001300","BTC":"0.000278","BWP":"10.474000","BZD":"2.018350","CAD":"1.328050","CDF":"1631.000000","CHF":"1.000300","CLF":"0.025048","CLP":"658.100000","CNY":"6.746600","COP":"3121.850000","CRC":"612.970000","CUP":"1.001395","CVE":"97.373000","CZK":"22.793600","DJF":"177.720000","DKK":"6.589100","DOP":"50.646500","DZD":"118.840000","EGP":"17.609500","ETB":"28.413000","ETH":"0.008377","EUR":"0.883085","FJD":"2.125900","GBP":"0.773115","GEL":"2.645000","GHS":"5.276200","GIP":"0.770005","GMD":"49.550000","GNF":"9127.200000","GTQ":"7.765200","GYD":"209.360000","HKD":"7.846950","HNL":"24.439500"
    


    Map mapJson = json.decode(response.body) returns the following format: 
    symbols_returned: 147, base: USD, data: AED: 3.672940, AFN: 75.617000, ALL: 109.780000, AMD: 490.740000, ANG: 1.797350, AOA: 313.147500, ARS: 37.864500, AUD: 1.408450, AWG: 1.800000, AZN: 1.702500, BAM: 1.727050, BBD: 2.004250, BCH: 0.008196, BDT: 83.950500, BGN: 1.726900, BHD: 0.377470, BIF: 1800.000000, BMD: 1.000000, BND: 1.357650, BOB: 6.919100, BRL: 3.729400, BSD: 1.001300, BTC: 0.000278, BWP: 10.474000, BZD: 2.018350, CAD: 1.328050, CDF: 1631.000000, CHF: 1.000300, CLF: 0.025048, CLP: 658.100000, CNY: 6.746600, COP: 3121.850000, CRC: 612.970000, CUP: 1.001395, CVE: 97.373000, CZK: 22.793600, DJF: 177.720000, DKK: 6.589100, DOP: 50.646500, DZD: 118.840000, EGP: 17.609500, ETB: 28.413000, ETH: 0.008377, EUR: 0.883085, FJD: 2.125900, GBP: 0.773115, GEL: 2.645000, GHS: 5.276200, GIP: 0.770005, GMD: 49.550000, GNF: 9127.200000, GTQ: 7.765200, GYD: 209.360000, HKD: 7.846950, HNL: 24.439500, HRK: 6.537500, HTG: 82.810000, HUF: 281.363000, IDR: 14042.950000, ILS: 3.640660, INR: 71.165000, IQD: 1194.800000

前者是String,后者是Map对象。我的问题是

    如何遍历和访问 Dart 中的每种货币: 例如var currencyValue = stringJson['AED']

以下是我尝试过的:stringJson 和 mapJson 都是从 future 方法 jsonTest() 返回的。

var stringJson = jsonOperation()

 stringJson.then((onValue)
  if(onValue != null)
        onValue.forEach((k,v)  
       print(onValue['AED'])
        print('$k,$v');                                          
    );
  
);

以上代码返回: print(onValue['AED']) 打印空 而打印('$k,$v');打印以下内容:

> symbols_returned,147 
>I/flutter ( 4575): base,USD 
>I/flutter ( 4575):
> data,AED: 3.673050, AFN: 74.450000, ALL: 110.130000, AMD: 489.850000,
> ANG: 1.795100, AOA: 313.147500, ARS: 38.223700, AUD: 1.415500, AWG:
> 1.794500, AZN: 1.705000, BAM: 1.728800, BBD: 2.001800, BCH: 0.008256, BDT: 83.907000, BGN: 1.735350, BHD: 0.377050, BIF: 1830.000000, BMD:
> 1.000000, BND: 1.350750, BOB: 6.913550, BRL: 3.764500, BSD: 1.000100, BTC: 0.000278, BWP: 10.505000, BZD: 2.010200, CAD: 1.330845, CDF:
> 1630.000000, CHF: 1.004050, CLF: 0.025048, CLP: 662.775000, CNY: 6.792400, COP: 3134.400000, CRC: 611.915000, CUP: 1.000550, CVE: 97.511500, CZK: 22.949000, DJF: 177.720000, DKK: 6.618750, DOP: 50.580000, DZD: 118.915000, EGP: 17.586000, ETB: 28.600000, ETH: 0.008363, EUR: 0.886920, FJD: 2.134350, GBP: 0.777245, GEL: 2.645000, GHS: 5.225000, GIP: 0.769990, GMD: 49.545000, GNF: 9220.000000, GTQ:
> 7.755600, GYD: 209.510000, HKD: 7.847850, HNL: 24.500000, HRK: 6.569900, HTG: 82.551000, HUF: 283.885000, IDR: 14100.500000, ILS: 3.645750, INR: 71.165000, IQD: 1190.000000, IRR: 42105.000000  

而不是以键值格式打印每种货币。问题是我无法访问每种货币的价值。

【问题讨论】:

【参考方案1】:

将解码后的值转换为Map,然后您可以访问'data' 键并将其转换为Map。然后,您可以迭代该映射中的键。

Future<void> printCurrencies() async 
  final response = await http.get('url');
  final decoded = jsonDecode(response) as Map;
  final data = decoded['data'] as Map;
  print(data['AED']); // prints 3.672940
  for (final name in data.keys) 
    final value = data[name];
    print('$name,$value'); // prints entries like "AED,3.672940"
  

请注意,如果您想要一个完全类型化的映射,您不能使用as Map&lt;String, num&gt;,因为在运行时具体化类型是Map&lt;String, dynamic&gt;。相反,您需要使用 cast 方法。 (decoded['data'] as Map).cast&lt;String, num&gt;();

【讨论】:

这有效,我不知道他为什么不接受你的回答。谢谢内特。【参考方案2】:

我最终能够以键值对格式访问每种货币。由于 json Map 格式如下所示:

 symbols_returned: 147, base: USD, data: AED: 3.672940, AFN: 75.617000, ALL: 109.780000, AMD: 490.740000, ANG: 1.797350, AOA: 313.147500, ARS: 37.864500, AUD: 1.408450, AWG: 1.800000, AZN: 1.702500, BAM: 1.727050, BBD: 2.004250, BCH: 0.008196, BDT: 83.950500, BGN: 1.726900, BHD: 0.377470, BIF: 1800.000000, BMD: 1.000000, BND: 1.357650, BOB: 6.919100, BRL: 3.729400, BSD: 1.001300, BTC: 0.000278, BWP: 10.474000, BZD: 2.018350, CAD: 1.328050, CDF: 1631.000000, CHF: 1.000300, CLF: 0.025048, CLP: 658.100000, CNY: 6.746600, COP: 3121.850000, CRC: 612.970000, CUP: 1.001395, CVE: 97.373000, CZK: 22.793600, DJF: 177.720000, DKK: 6.589100, DOP: 50.646500, DZD: 118.840000, EGP: 17.609500, ETB: 28.413000, ETH: 0.008377, EUR: 0.883085, FJD: 2.125900, GBP: 0.773115, GEL: 2.645000, GHS: 5.276200, GIP: 0.770005, GMD: 49.550000, GNF: 9127.200000, GTQ: 7.765200, GYD: 209.360000, HKD: 7.846950, HNL: 24.439500, HRK: 6.537500, HTG: 82.810000, HUF: 281.363000, IDR: 14042.950000, ILS: 3.640660, INR: 71.165000, IQD: 1194.800000

我使用了print(onValue['data']['AED']),它返回 3.672940。其中数据(在方括号中)是 json 集合的名称,AED(也在方括号中)是我打算访问其值的特定货币。 要遍历 json 映射,请使用以下代码:

                              stringJson().then((onValue) 
                              onValue['data'].forEach((k,v)                                      
                              //the following access AUD currency value
                              print(onValue['data']['AUD']);
                              //the following print all the currency in 
                              key-value format
                              print('$k,$v');                                     
                            );

希望这对某人有所帮助。

【讨论】:

【参考方案3】:

我相信您实际上是在迭代父对象,该对象具有包含值的数据属性。您需要迭代 data 属性。

所以要获取您可以使用的值:

  stringJson.then((onValue)
    if(onValue != null)
      onValue.data.forEach((k,v)  // add .data here
        print(onValue['AED'])
        print('$k,$v');                                          
      );
    
  );

【讨论】:

感谢您的回复。 IDE 编辑器抱怨 onValue 没有“数据”作为它的方法。确切的错误表达式是:“没有为类 Map 定义 getter 数据”。请注意 stringJson 方法返回一个 Map 对象。再次感谢 data 不是字段,也不是地图中的键。 onValue['data'] 会让你更接近。

以上是关于如何在 Flutter Dart 中迭代 JSON Map 并检索键值结果?的主要内容,如果未能解决你的问题,请参考以下文章

如何在 dart/flutter 中提取 JSON 子数据

如何在 dart/flutter 中解码 json 数组?

如何在 dart/flutter 中解码复杂的 json?

使用 Flutter FutureBuilder 迭代 JSON 中的对象数组

如何在Dart / flutter中映射和显示嵌套的JSON?

在 Flutter/Dart 中从 JSON 数组中提取数据