如何打印原始变量';从函数返回后的Python中的名称?
我有enum并使用诸如如何打印原始变量';从函数返回后的Python中的名称?,python,variables,Python,Variables,我有enum并使用诸如myEnum.SomeNameA,myEnum.SomeNameB等变量。当我从函数返回其中一个变量时,是否可以打印它们的名称(例如myEnum.SomeNameA),而不是它们返回的值?简短回答:否 详细回答:这是可能的一些丑陋的黑客使用回溯,检查等,但它通常不推荐用于生产代码。例如,请参见: 也许可以使用变通方法将值转换回名称/表示字符串。如果您发布更多的示例代码和详细信息,说明您想要这些代码的目的,也许我们可以提供更深入的帮助。据我所知,这需要一些反思。您可以
myEnum.SomeNameA
,myEnum.SomeNameB
等变量。当我从函数返回其中一个变量时,是否可以打印它们的名称(例如myEnum.SomeNameA
),而不是它们返回的值?简短回答:否
详细回答:这是可能的一些丑陋的黑客使用回溯,检查等,但它通常不推荐用于生产代码。例如,请参见:
也许可以使用变通方法将值转换回名称/表示字符串。如果您发布更多的示例代码和详细信息,说明您想要这些代码的目的,也许我们可以提供更深入的帮助。据我所知,这需要一些反思。您可以尝试使用inspect模块 在此之前,您可能需要尝试一些简单的方法:
编辑:
我只是注意到这不是你想要的。在这种情况下,添加一个 dict和函数可以工作
问题并不是微不足道的,因此您可能希望使用经过测试的解决方案。当然,如果可以,最好避免这种情况。您可以将规范名称存储为实例的属性,然后将其分配给具有相同名称的变量。这可能会奏效:
class MyEnum(object):
def __new__(cls, name):
try:
return getattr(MyEnum, name)
except AttributeError:
e = super(MyEnum, cls).__new__(cls)
e.name = name
setattr(MyEnum, name, e)
return e
无论如何,这并不是一件特别“Pythonic”的事情。补充一些概念
Python“变量”只是对值的引用。每个值都占用给定的内存位置(请参见id()
)
从上面,您可能注意到值“1”存在于存储器位置10052552处。在这个解释器实例中,它被引用了569次
>>> MYVAR = 1
>>> sys.getrefcount(1)
570
现在,请注意,因为还有另一个名称绑定到此值,所以引用计数增加了1
基于这些事实,判断哪个变量名指向某个值是不现实的/不可能的
我认为解决您的问题的最佳方法是将映射和函数添加到枚举引用中,并返回到字符串名称
myEnum.get_name(myEnum.SomeNameA)
如果您想要示例代码,请发表评论。Erlang有一个称为“原子”的概念——它们类似于字符串常量或枚举。考虑使用字符串常量作为枚举的值——与枚举的名称相同。< P>只使用要打印的文本作为枚举的值,如
class MyEnum (object):
valueA = "valueA"
valueB = "valueB"
在Python中,比较字符串的标识几乎和比较整数值一样有效(这是因为字符串是不可变的,因为它们具有哈希值)
当然,首先有更简单的方法来创建枚举:
class Enum (object):
def __init__(self, *values):
for v in values:
self.__dict__[v] = v
然后,创建如下枚举:
MyEnum = Enum("valueA", "valueB")
ans访问方式与上述相同:
MyEnum.valueA
没有唯一的或原始的变量名 就像你在门廊上找到的那只猫的名字一样:猫(对象)本身不能告诉你它的名字,而且它也不在乎——所以要知道它叫什么,唯一的办法就是问你所有的邻居(名称空间)它是不是他们的猫(对象) …如果你发现它有很多名字,或者根本没有名字,不要惊讶 < P> <强> Fredrik Lundh,3月2000日,回答了“当我有PyObjult*时,如何从C++中获得变量名”的问题?<强> < /P> 仔细想想: 由于Python不提供本机枚举类型,因此不应要求使用一种,而应使用另一种更强大的构造来构建程序。否则,下一步将始终是“为什么Python没有
开关…:
语句,如何最好地模拟它?”
由于枚举通常用于定义某种状态,因此更好的方法是:
创建一个基类,该基类定义属于某个状态的所有抽象属性、属性和方法。然后,对于每个状态,派生一个子类来实现该状态的特定行为。然后,您可以传递这些类(或其实例)来处理状态及其行为
如果您使用类而不是实例(Python的“单例”方式),您可以通过检查任何给定的状态(这不是必须的),如果当前的状态是StateA:
(注意是而不是=
),在比较整数值时没有性能损失
当然,您可以定义一个name
属性和一个\u str\u()
方法来访问和打印州名。这个问题有两个答案:是和否
如果您知道enums类对象以及该类中的所有名称(或至少是唯一前缀),那么是否有100个名称引用一个整数并不重要
对于上面的示例,您可以使用以下方法检查“Enum.\uuu dict\uuu
”:
在这种情况下,您甚至不必知道所有枚举名称。如果枚举的实现方式不同,那么您可能需要使用不同的hack。那里
MyEnum.valueA
Can you do it? -- Yes (in most cases)
Is it worth it? -- No (in most cases)
class Enum:
A = 1
B = 2
>>> getEnum = lambda: Enum.A
>>> namestr(getEnum(), Enum.__dict__)
>>> ['A']
>>> from enum import Enum
>>> class Type(Enum):
... AB, SBS, INTERLACED, SPLIT = range(4)
...
>>> Type.AB
<Type.AB: 0>
>>> print(Type.AB)
Type.AB
>>> Type.AB.name
'AB'
>>> Type.AB.value
0
>>> Type(0)
<Type.AB: 0>
>>> def varname(v): d = globals(); return [k for k in d if d[k] == v]
...
>>> def varnameis(v): d = globals(); return [k for k in d if d[k] is v]
...
>>> foo = {'a':'aap'}
>>> bar = {'a':'aap'}
>>> varname(foo)
['foo', 'bar']
>>> varnameis(foo)
['foo']
>>> foo = "A"; bar = "A"
>>> varnameis("A")
['foo', 'bar']
>>> foo = "An immutable value."; bar = "An immutable value."
>>> varnameis("An immutable value.")
[]
>>> foo = "An immutable value."; bar = "An immutable value."; varnameis("An immutable value.")
['foo', 'bar']
>>> import sys; sys.version
'3.6.6 (v3.6.6:4cf1f54eb7, Jun 27 2018, 02:47:15) [MSC v.1900 32 bit (Intel)]'
>>> def varname(v, scope=None): d = globals() if not scope else vars(scope); return [k for k in d if d[k] == v]
...
>>> import time
>>> time.timezone
-3600
>>> varname(-3600)
[]
>>> varname(-3600, time)
['timezone']
import inspect
def printVariableName(abc):
newvar=inspect.stack()[1][4][0]
print(newvar.split("(")[1].split(")")[0])
noob=10
printVariableName(noob)
noob
my_nice_variable_name = 'test'
print(f'{my_nice_variable_name=}')
# Output:
# my_nice_variable_name='test'
my_variable = some_object
f'{my_variable=}'.split('=', 1)[0]