Python 为继承 class 中的基础 class 方法抛出属性错误
Python throws Attribute Error for base class method in inherited class
我在调用 BaseSocketDataHandler
class 函数时遇到如下属性错误,方法是从键名中获取字符串作为字符串,并在迭代 [= 时使用 self.method_name = getattr(self, "self.__process_" + key.lower().replace(" ", "_"))
将其转换为方法名16=]
AttributeError: 'DataHandler' object has no attribute
'self.__process_info'
我不明白为什么会出现此错误。通过字符串调用函数是正确的方法,还是我应该做其他事情?
class BaseSocketDataHandler(object):
def __init__(self, sql_address, sql_user, sql_pswd, sql_db_name):
.....
self.db_connector = MySqlConnector(address=sql_address, suser=sql_user, spwd=sql_pswd, db_name=sql_db_name)
.....
self.info_dict = dict()
self.info_dict_map = {"date_time": (0, 12), "info_len": (12, 13), "info": (13, 14), "reserved": (36, 37)}
self.hex_data_dict = {"data_content": "0123456789abcdef10111213141516171819"
@staticmethod
def __convert_to_int(data):
return int(data, 16)
@staticmethod
def __process_reserved(data):
return data
def __process_date_time(self, date_time_in_hex):
date_time = tuple()
for x in date_time_in_hex:
date_time += self.__convert_to_int(x)
return date_time
def __process_info_len(self, info_len):
return self.__convert_to_int(info_len)
def __process_info(self, info):
return self.__convert_to_int(number_of_sat)
def make_info(self):
for key, val in self.info_dict_map.items():
method_name = getattr(self, "self.__process_" + key.lower().replace(" ", "_"))
key_var = key
setattr(self, key_var, method_name(self.hex_data_dict["data_content"][val[0]: val[1]]))
self._info_dict.update({key: key_var})
self.method_name = None
class DataHandler(BaseSocketDataHandler):
def __init__(self):
super(DataHandler, self).__init__(sql_address, sql_user, sql_pswd, sql_db_name)
def run_forever(self):
while True:
try:
self.make_info()
except Exception as uee:
self.log.exception(self._log_msg(uee))
break
因为"process"前面有两个下划线。这称为名称修改。来自 python 文档:
Since there is a valid use-case for class-private members (namely to
avoid name clashes of names with names defined by subclasses), there
is limited support for such a mechanism, called name mangling. Any
identifier of the form __spam (at least two leading underscores, at
most one trailing underscore) is textually replaced with
_classname__spam, where classname is the current class name with leading underscore(s) stripped. This mangling is done without regard
to the syntactic position of the identifier, as long as it occurs
within the definition of a class.
我在调用 BaseSocketDataHandler
class 函数时遇到如下属性错误,方法是从键名中获取字符串作为字符串,并在迭代 [= 时使用 self.method_name = getattr(self, "self.__process_" + key.lower().replace(" ", "_"))
将其转换为方法名16=]
AttributeError: 'DataHandler' object has no attribute 'self.__process_info'
我不明白为什么会出现此错误。通过字符串调用函数是正确的方法,还是我应该做其他事情?
class BaseSocketDataHandler(object):
def __init__(self, sql_address, sql_user, sql_pswd, sql_db_name):
.....
self.db_connector = MySqlConnector(address=sql_address, suser=sql_user, spwd=sql_pswd, db_name=sql_db_name)
.....
self.info_dict = dict()
self.info_dict_map = {"date_time": (0, 12), "info_len": (12, 13), "info": (13, 14), "reserved": (36, 37)}
self.hex_data_dict = {"data_content": "0123456789abcdef10111213141516171819"
@staticmethod
def __convert_to_int(data):
return int(data, 16)
@staticmethod
def __process_reserved(data):
return data
def __process_date_time(self, date_time_in_hex):
date_time = tuple()
for x in date_time_in_hex:
date_time += self.__convert_to_int(x)
return date_time
def __process_info_len(self, info_len):
return self.__convert_to_int(info_len)
def __process_info(self, info):
return self.__convert_to_int(number_of_sat)
def make_info(self):
for key, val in self.info_dict_map.items():
method_name = getattr(self, "self.__process_" + key.lower().replace(" ", "_"))
key_var = key
setattr(self, key_var, method_name(self.hex_data_dict["data_content"][val[0]: val[1]]))
self._info_dict.update({key: key_var})
self.method_name = None
class DataHandler(BaseSocketDataHandler):
def __init__(self):
super(DataHandler, self).__init__(sql_address, sql_user, sql_pswd, sql_db_name)
def run_forever(self):
while True:
try:
self.make_info()
except Exception as uee:
self.log.exception(self._log_msg(uee))
break
因为"process"前面有两个下划线。这称为名称修改。来自 python 文档:
Since there is a valid use-case for class-private members (namely to avoid name clashes of names with names defined by subclasses), there is limited support for such a mechanism, called name mangling. Any identifier of the form __spam (at least two leading underscores, at most one trailing underscore) is textually replaced with _classname__spam, where classname is the current class name with leading underscore(s) stripped. This mangling is done without regard to the syntactic position of the identifier, as long as it occurs within the definition of a class.