繁体   English   中英

Python:通过函数放置多个变量的有效方法

[英]Python: Efficient way to put multiple variables through a function

我有一堆等于从数据库中提取的值的变量。 有时,数据库没有值并返回“ NoneType”。 我正在使用这些变量,并使用它们来构建XML文件。 当变量为NoneType时,它将导致XML值读取为“ None”,而不是我希望的空白。

我的问题是:是否存在一种有效的方法来一次遍历所有变量并搜索NoneType,如果找到,将其转换为空白字符串?

例如

from types import *

[Connection to database omitted]

color = database.color
size = database.size
shape = database.shape
name = database.name
... etc

我显然可以做这样的事情:

if type(color) is NoneType:
  color = ""

但这对于我拥有的15个以上变量将变得乏味。 有没有更有效的方法来检查每个变量的类型,然后根据需要进行更正? 像创建一个函数来执行检查/更正,并具有通过该函数传递每个变量的自动方法?

此处给出的所有解决方案将使您的代码更短,更少繁琐,但是,如果您确实有很多变量,我想您将不胜感激,因为它不会使您为每个变量甚至添加一个额外的代码字符

class NoneWrapper(object):
    def __init__(self, wrapped):
        self.wrapped = wrapped

    def __getattr__(self, name):
        value = getattr(self.wrapped, name)
        if value is None:
            return ''
        else:
            return value

mydb = NoneWrapper(database)
color = mydb.color
size = mydb.size
shape = mydb.shape
name = mydb.name

# All of these will be set to an empty string if their
# original value in the database is none

编辑

我以为这很明显,但是我一直忘记花时间才能使所有有趣的Python魔术变成第二天性。 :)那么, NoneWrapper如何NoneWrapper其魔力? 真的,这非常简单。 每个python类都可以定义一些易于识别的“特殊”方法名称,因为它们总是被两侧的两个下划线所包围。 这些方法中最常见和最著名的是__init__() ,它可以初始化类的每个实例,但是还有许多其他有用的特殊方法,其中之一是__getattr__() 每当有人尝试访问属性时,都会调用此方法。 类实例的实例,您可以对其进行自定义以自定义属性访问。

NoneWrapper的作用是重写getattr ,因此,每当有人尝试读取mydb的属性(这是一个NoneWrapper实例)时,它都会从包装的对象(在本例中为database )中读取具有指定名称的属性,并返回它-除非它的值为None,在这种情况下,它将返回一个空字符串。

我在这里应该补充一点,对象变量和方法都是属性,实际上,对于Python,它们本质上是同一件事:所有属性都是可以更改的变量,而方法恰好是将其值设置为a的变量。特殊类型的功能(绑定方法)。 因此,您还可以使用getattr ()来控制对函数的访问,这可能会导致许多有趣的用途。

您可以简单地使用:

color = database.color or ""

另一种方法是使用函数:

def filter_None(var):
    "" if (a is None) else a

color = filter_None(database.color)

我不知道数据库对象的结构,但是另一种解决方案是修改database对象,例如:

def myget(self, varname):
   value = self.__dict__[varname]
   return "" if (value is None) else value

DataBase.myget = myget
database = DataBase(...)
[...]
color = database.myget("color")

您可以使用描述符或属性做得更好

尽管我不知道这是否是最好的方法,但我将这样做的方法是放入要检查的变量,然后使用for语句遍历列表。

check_vars = [color,size,shape,name]
for var in check_vars:
    if type(var) is NoneType:
        var = ""

要添加变量,您要做的就是将它们添加到列表中。

如果您一次已经有了一个,那么写它就不再那么长了:

def none_to_blank(value):
    if value is None:
        return ""
    return value

color = none_to_blank(database.color)
size = none_to_blank(database.size)
shape = none_to_blank(database.shape)
name = none_to_blank(database.name)

顺便提一句,一般不建议使用“ import *”。 仅导入您正在使用的内容。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM