我已經搜索但沒有找到好的答案,所以我會發布它:)
我目前正在創建一個 python 模塊,它使用一個 http get 請求來獲取一個物件,其中包含一堆這樣結構的資料。
- 主要群體
- 第一組
- 資料1
- 資料2
- 第 2 組
- 資料1
- 資料2
- 第 3 組
- 資料1
- 資料2
- 第一組
我創建了一個資料類,它只列出了所有這些變數,例如
@dataclass
class MyData:
grp1_data1: str
grp1_data2: str
grp2_data1: str
grp2_data2: str
grp3_data1: str
grp3_data2: str
@classmethod
def from_dict(cls, data: dict) -> "MyData":
return cls(
grp1_data1=data["Main group"]["Group 1"]["data1"],
grp1_data2=data["Main group"]["Group 1"]["data2"],
# And so on ...
)
我正在尋找的是一種將資料類中的變數分組到類似于結構的方法,這樣我就不需要在變數名中混合組名和資料名。
我對 python 很陌生,我不知道什么樣的組功能可以與資料類一起使用,如果有的話?
我希望能夠寫出類似grp1.data1=data["Main group"]["Group 1"]["data1"]或類似的東西。
uj5u.com熱心網友回復:
您的問題有點不清楚,但正如評論中所建議的那樣,最好將單個模型作為表示您的組資料的資料類(即包含data1和data2欄位的模型)并定義一個構建組映射的輔助函式命名模型實體,如下所示。
注意:這假設您使用的是 Python 3.8 。對于早期版本,我會做兩件事:
__future__如果需要,請洗掉匯入,而是從模塊匯入Type和,因為內置型別不支持 Python 3.8 或更早版本中的下標值。Dicttyping- 洗掉
:=Python 3.8 中引入的 walrus運算子的用法,而是使用它后面的注釋行。
# Future import to allow the `int | str` syntax below
# Can be removed for Python 3.10
from __future__ import annotations
from dataclasses import dataclass
from typing import TypeVar
# Create a type that can be `MyData`, or any subclass
D = TypeVar('D', bound='MyData')
@dataclass
class MyData:
data1: str
data2: str
@classmethod
def from_dict(cls: type[D], data: dict, group_num: int | str) -> D:
return cls(
data1=data['MG'][f'G {group_num}']['data1'],
data2=data['MG'][f'G {group_num}']['data2'],
)
@classmethod
def group_to_data(cls: type[D], data: dict) -> dict[int, D]:
return {(group_num := int(group_key.split()[-1])): cls.from_dict(
data, group_num)
for group_key in data['MG']}
# For Python 3.7 or lower, uncomment and use the below instead
# ret_dict = {}
# for group_key in data['MG']:
# group_num = int(group_key.split()[-1])
# ret_dict[group_num] = cls.from_dict(data, group_num)
#
# return ret_dict
測驗代碼:
def main():
from pprint import pprint
my_data = {
'MG': {
'G 1': {
'data1': 'hello',
'data2': 'World!',
},
'G 2': {
'data1': '',
'data2': 'Testing',
},
'G 3': {
'data1': 'hello 123',
'data2': 'world 321!'
}
}
}
group_to_data = MyData.group_to_data(my_data)
pprint(group_to_data)
# True
assert group_to_data[1] == MyData('hello', 'World!')
輸出:
{1: MyData(data1='hello', data2='World!'),
2: MyData(data1='', data2='Testing'),
3: MyData(data1='hello 123', data2='world 321!')}
uj5u.com熱心網友回復:
可以使用類組合創建多級資料類來做你想做的事情(也許不像 C 型別結構那么優雅,但它可以作業):
@dataclass
class Top:
@dataclass
class Child:
data1: str
data2: str
Group1: Child
Group2: Child
Group3: Child
inst = Top(
Group1=Top.Child('a','b'),
Group2=Top.Child('x', 'y'),
Group3=Top.Child('101', '102')
)
# check it:
@dataclass
class Top:
@dataclass
class Child:
data1: str
data2: str
Group1: Child
Group2: Child
Group3: Child
# create an instance
inst = Top(
Group1=Top.Child('a','b'),
Group2=Top.Child('x', 'y'),
Group3=Top.Child('101', '102')
)
# check it:
assert inst.Group2.data2 == 'y'
關鍵是您必須將所有子成員也定義為資料類(或更準確地說,定義為類)。您可以就地(如上)或單獨定義子類。
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/330782.html
標籤:Python json http 结构 python-数据类
上一篇:網路for回圈異步
下一篇:為什么HTTP/2使用偽頭欄位?
