[英]How to sort JSON file by value Python
我有一個大的 JSON 文件,其中包含如下時區:
{
"timezones":[
{
"id":1,
"name":"(UTC) Coordinated Universal Time",
"utc_offset":"+0"
},
{
"id":2,
"name":"(UTC+8:45) Australian Central Standard Time",
"utc_offset":"+8:45"
},
{
"id":3,
"name":"(UTC-5) Acre Time",
"utc_offset":"-5"
},
{
"id":4,
"name":"(UTC+8:45) Australian Central Western Standard Time",
"utc_offset":"+8:45"
}
]
}
我正在嘗試根據from - to +
的utc_offset
值對其進行排序,如果utc_offset
相同,則按字母順序按name
排序。 所以想要的結果應該是這樣的:
{
"timezones":[
{
"id":3,
"name":"(UTC-5) Acre Time",
"utc_offset":"-5"
},
{
"id":1,
"name":"(UTC) Coordinated Universal Time",
"utc_offset":"+0"
},
{
"id":2,
"name":"(UTC+8:45) Australian Central Standard Time",
"utc_offset":"+8:45"
},
{
"id":4,
"name":"(UTC+8:45) Australian Central Western Standard Time",
"utc_offset":"+8:45"
}
]
}
我嘗試使用以下代碼:
lines = lines.sort(int(json['timezones']['utc_offset']), reverse=True)
print(lines)
但它顯示錯誤AttributeError: 'dict' object has no attribute 'sort'
我該怎么做?
也許像這樣使用正則表達式來解析utc_offset
:
adict = {
"timezones": [
{
"id": 1,
"name": "(UTC) Coordinated Universal Time",
"utc_offset": "+0"
},
{
"id": 2,
"name": "(UTC+8:45) Australian Central Standard Time",
"utc_offset": "+8:45"
},
{
"id": 3,
"name": "(UTC-5) Acre Time",
"utc_offset": "-5"
},
{
"id": 4,
"name": "(UTC+8:45) Australian Central Western Standard Time",
"utc_offset": "+8:45"
}
]
}
timezones = adict['timezones']
pattern = re.compile(r'^(?P<sign>[+-])(?P<hour>\d+):?(?P<minutes>\d+)?')
def get_time(string):
m = pattern.match(string)
if not m:
return False
sign, hour, minutes = m.groupdict().values()
result = int(hour) * 60 + (int(minutes) if minutes else 0)
result = -result if sign == '-' else result
return result
print(sorted(timezones, key=lambda x: (get_time(x['utc_offset']), x['name'])))
Output:
[
{'id': 3, 'name': '(UTC-5) Acre Time', 'utc_offset': '-5'},
{'id': 1, 'name': '(UTC) Coordinated Universal Time', 'utc_offset': '+0'},
{'id': 2, 'name': '(UTC+8:45) Australian Central Standard Time', 'utc_offset': '+8:45'},
{'id': 4, 'name': '(UTC+8:45) Australian Central Western Standard Time', 'utc_offset': '+8:45'}
]
json = {
"timezones":[
{
"id":1,
"name":"(UTC) Coordinated Universal Time",
"utc_offset":"+0"
},
{
"id":2,
"name":"(UTC+8:45) Australian Central Standard Time",
"utc_offset":"+8:45"
},
{
"id":3,
"name":"(UTC-5) Acre Time",
"utc_offset":"-5"
},
{
"id":4,
"name":"(UTC+8:45) Australian Central Western Standard Time",
"utc_offset":"+8:45"
}
]
}
def to_mins(e):
offset = e['utc_offset']
sign = 1 if offset[0] == '+' else -1
hm = offset[1:].split(':')
h, m = (hm[0], 0) if len(hm) == 1 else hm
return sign * (60 * int(h) + int(m))
print(sorted(json['timezones'], key=to_mins))
印刷
[{'id': 3, 'name': '(UTC-5) Acre Time', 'utc_offset': '-5'},
{'id': 1, 'name': '(UTC) Coordinated Universal Time', 'utc_offset': '+0'},
{'id': 2,
'name': '(UTC+8:45) Australian Central Standard Time',
'utc_offset': '+8:45'},
{'id': 4,
'name': '(UTC+8:45) Australian Central Western Standard Time',
'utc_offset': '+8:45'}]
所以首先我們將時區字符串轉換為數值,然后使用排序后的 function 進行排序。 如果要按降序獲得結果,可以將 boolean 參數的值反向更改。
def get_minutes_tz(str_tz):
min_tz = None
# add more checks on the format of the timezone string (you can also use regexes)
if len(str_tz)>0 and isinstance(str_tz, str) and (str_tz.startswith('+') or str_tz.startswith('-')):
splits = str_tz[1:].split(':')
min_tz = int(str_tz[0] + str(int(splits[0])*60 if len(splits)>0 else 0 + int(splits[1] if len(splits)>1 else 0)))
return min_tz
sorted(d['timezones'], key=lambda k: get_minutes_tz(k['utc_offset']),
reverse=False)
結果:
[{'id': 3, 'name': '(UTC-5) Acre Time', 'utc_offset': '-5'},
{'id': 1, 'name': '(UTC) Coordinated Universal Time', 'utc_offset': '+0'},
{'id': 2,
'name': '(UTC+8:45) Australian Central Standard Time',
'utc_offset': '+8:45'},
{'id': 4,
'name': '(UTC+8:45) Australian Central Western Standard Time',
'utc_offset': '+8:45'}]
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.