在python中动态创建变量

时间:2018-07-05 15:55:57

标签: python oop attributes

我有一个文件,存储变量名和值,如下所示:

name,David
age,16
score,91.2
...

我想编写一个python脚本来读取文件并自动在对象中创建变量,而无需我实际进行操作,例如:

self.name='David'
self.age=16
self.score=91.2

有可能这样做吗? 我这样做的原因是,可能文件中包含非常不同类型的变量,这些变量我之前都不知道。

3 个答案:

答案 0 :(得分:1)

我建议使用更简洁的方式来存储数据(例如JSON甚至是python的pickle模块)。但这不在此答案的范围内。假设您要使用数据格式,则可以这样读取文件:

my_object = xyz()
variables_file = open("variables.txt", "r")
for line in variables_file:
    line = line.rstrip("\n") # remove the linebreak at the end of each line
    line = line.split(",") # split the line at the comma -> generates a list
    setattr(my_object, line[0], line[1]) # sets the variable as attribute of my_object
print("And the name is: "+my_object.name)+"!!!")

更好的方法是使用字典,这比java的方法更具Python风格:

configs = {}

并分配以下值:

configs["name"] = "David"

或像上面的示例那样通过遍历文件来动态地执行此操作,只是不使用setattr并使用:

configs[line[0]] = line[1]

答案 1 :(得分:1)

  

我这样做的原因是可能存在包含非常不同的文件   我事先不知道的变量类型。

如果这是主要原因,则应使用字典。没有更好的方法。看到标记的重复项。


原始解决方案

虽然通常建议在字典中保留类似变量,但是如果变量描述了一个类实例,则直接分配它们没有什么害处。如果字典键是任意的,建议您将字典传递给该类。

根据@Delgan的评论,您可以从文本文件创建字典,然后在迭代字典项时使用setattr。以下是使用csv模块并将逻辑包装在函数中的解决方案。

import csv

def add_attributes(obj, fn):

    # create dictionary from text file
    with open(fn, 'r') as fin:
        d = dict(csv.reader(fin))

    # iterate dictionary and add attributes
    for name, value in d.items():
        setattr(obj, name, value)

    return obj

class myClass():
    def __init__(self):
        pass

A = myClass()

add_attributes(A, 'file.csv')

print(A.age)  # 16

答案 2 :(得分:-1)

创建班级时,您应该知道班级将拥有多少个变量。

为类中的对象动态创建新变量是一个坏主意,因为您不能使用变量进行操作。

例如假设您的班级有变量nameagemarksaddress。您可以对此进行操作,因为您已经知道变量。

但是,如果尝试动态存储变量,那么您将不知道存在哪些变量,并且无法对它们执行操作。

如果只想显示文件中存在的变量及其值,则可以使用字典来存储变量及其各自的值。将所有变量存储在字典中之后,您可以显示变量及其值:

dict={}
with open('filename.txt') as f:
data = f.readlines()
for i in data:
    i = i.rstrip()
    inner_data = i.split(',')
    variable = inner_data[0]
    value = inner_data[1]
    dict.update({variable:value})

print(dict)

这将打印文件中的所有变量及其值。

但是该文件应包含以下格式的变量和值:

name,Sam
age,10
address,Mumbai
mobile_no,199204099
....
....