【问题标题】:How to parse values from JSON in Python如何在 Python 中解析 JSON 中的值
【发布时间】:2019-08-01 09:29:33
【问题描述】:

早上好;我正在尝试从 URL 生成的 JSON 文件中提取一些键值。

我能够毫无问题地从 URL 中提取 JSON(打印第 8 行以供参考)

def get_url():
    api_conditions_url = 'http://magicseaweed.com/api/' + API_KEY + '/forecast/?spot_id=' + PUTSBOROUGH_SPOT_ID
    print('Collecting data from - ' + api_conditions_url)
    try:
        f = urlopen(api_conditions_url)
    except:
        return []
    json_currently = f.read()
    print(json_currently)
    f.close()
    return json.loads(json_currently)

def main():
    curr_conditions = get_url()
    if ("absMinBreakingHeight" not in curr_conditions["swell"]):
        print ("Error #001 JSON call failed, check your query is correct!]\n")
        exit()
    else:
        print('it worked')

if __name__ == "__main__":
    main()

JSON 文件如下所示:


{  
      "timestamp":1564617600,
      "localTimestamp":1564617600,
      "issueTimestamp":1564617600,
      "fadedRating":0,
      "solidRating":0,
      "swell":{  
         "absMinBreakingHeight":1.3,
         "absMaxBreakingHeight":2.03,
         "probability":100,
         "unit":"ft",
         "minBreakingHeight":1,
         "maxBreakingHeight":2,
         "components":{  
            "combined":{  
               "height":3,
               "period":6,
               "direction":75.97,
               "compassDirection":"WSW"
            },
            "primary":{  
               "height":2.5,
               "period":6,
               "direction":65.06,
               "compassDirection":"WSW"
            },
            "secondary":{  
               "height":1.1,
               "period":6,
               "direction":160.71,
               "compassDirection":"NNW"
            }
         }
      },
      "wind":{  
         "speed":5,
         "direction":127,
         "compassDirection":"NW",
         "chill":60,
         "gusts":6,
         "unit":"mph"
      },
      "condition":{  
         "pressure":1017,
         "temperature":61,
         "weather":"10",
         "unitPressure":"mb",
         "unit":"f"
      },
      "charts":{  
         "swell":"https:\/\/charts-s3.msw.ms\/archive\/wave\/750\/1-1564617600-1.gif",
         "period":"https:\/\/charts-s3.msw.ms\/archive\/wave\/750\/1-1564617600-2.gif",
         "wind":"https:\/\/charts-s3.msw.ms\/archive\/gfs\/750\/1-1564617600-4.gif",
         "pressure":"https:\/\/charts-s3.msw.ms\/archive\/gfs\/750\/1-1564617600-3.gif",
         "sst":"https:\/\/charts-s3.msw.ms\/archive\/sst\/750\/1-1564617600-10.gif"
      }
   },

我在尝试解析 JSON 文件时收到以下错误 -

if ("absMinBreakingHeight" not in curr_conditions["swell"]):

TypeError: 列表索引必须是整数或切片,而不是 str"

【问题讨论】:

  • 看起来 curr_conditions 是一个列表,而您只向我们展示了其中的一部分。
  • 你的tryexcept 块中的f = urlopen(api_conditions_url) 是否有可能失败并且get_url 函数返回一个空列表?
  • @AlexHall - 如何将其从列表更改为我可以调用的内容。我使用相同的代码毫无问题地提取了不同的 JSON 文件。我比较了两个 JSON 文件,看起来一样。
  • 请分享完整的 JSON
  • 我认为您的 json 可能是字典列表,即[{}, {}],您可能需要对其进行迭代并检查。即curr_conditions[0]["swell"]

标签: python json


【解决方案1】:

知道了。 JSON 是一个字典列表(见下文)
https://magicseaweed.com/developer/forecast-api

您将收到一个 JSON 数组,其中包含一系列代表特定时间范围内预测的数据,如下所示:

所以你的代码应该在它上面做一个 for 循环。

for forecast in forecasts:
    # your logic goes here

JSON

[{
timestamp: 1366902000,
localTimestamp: 1366902000,
issueTimestamp: 1366848000,
fadedRating: 0,
solidRating: 0,
swell: {
    minBreakingHeight: 1,
    absMinBreakingHeight: 1.06,
    maxBreakingHeight: 2,
    absMaxBreakingHeight: 1.66,
    unit: "ft",
    components: {
         combined: {
         height: 1.1,
         period: 14,
         direction: 93.25,
         compassDirection: "W"
    },
    primary: {
         height: 1,
         period: 7,
         direction: 83.37,
         compassDirection: "W"
    },
    secondary: {
         height: 0.4,
         period: 9,
         direction: 92.32,
         compassDirection: "W"
    },
    tertiary: {
         height: 0.3,
         period: 13,
         direction: 94.47,
         compassDirection: "W"
     }
     }
},
wind: {
     speed: 10,
     direction: 85,
     compassDirection: "W",
     chill: 15,
     gusts: 13,
     unit: "mph"
},
condition: {
     pressure: 1020,
     temperature: 18,
     unitPressure: "mb",
     unit: "c"
},
charts: {
    swell: "http://cdn.magicseaweed.com/wave/750/1-1366902000-1.gif",
    period: "http://cdn.magicseaweed.com/wave/750/1-1366902000-2.gif",
    wind: "http://cdn.magicseaweed.com/gfs/750/1-1366902000-4.gif",
    pressure: "http://cdn.magicseaweed.com/gfs/750/1-1366902000-3.gif",
    sst: "http://cdn.magicseaweed.com/sst/750/1-1366902000-10.gif"
}
}]

【讨论】:

    【解决方案2】:

    你必须将字符串转换为dict,像这样改变你的main函数。

    import ast 
    
    def main():
        curr_conditions = get_url()
        curr_conditions = ast.literal_eval(curr_conditions) # add this sentence
        if ("absMinBreakingHeight" not in curr_conditions["swell"]):
            print ("Error #001 JSON call failed, check your query is correct!]\n")
            exit()
        else:
            print('it worked')
    
    
    
    
    
    

    【讨论】:

      【解决方案3】:

      感谢大家的意见。我尝试了所有方法,一切都是正确的 - JSON 是一个字典列表。将“[0]”应用于“”curr_conditions[0][“swell”])“”部分允许我从 JSON 中提取值。

      def get_url():
          api_conditions_url = 'http://magicseaweed.com/api/' + API_KEY + '/forecast/?spot_id=' + PUTSBOROUGH_SPOT_ID
          print('Collecting data from - ' + api_conditions_url)
          try:
              f = urlopen(api_conditions_url)
          except:
              return []
          json_currently = f.read()
          print(f)
          f.close()
          return json.loads(json_currently)
      
      def main():
          curr_conditions = get_url()
          if ("absMinBreakingHeight" not in curr_conditions[0]["swell"]):
              print ("Error #001 JSON call failed, check your query is correct!]\n")
              exit()
          else:
              print(curr_conditions[0]["swell"]["absMinBreakingHeight"])
      
      if __name__ == "__main__":
          main()
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-06-30
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多