我正在尝试将用PHP编写的lib重写为python。它处理所有sphinx请求。在init函数中,我试图设置默认搜索和匹配模式,但我遇到了一个小问题。我从配置文件中获取模式。
在PHP中,您需要使用常量作为输入:
$this->sphinx->SetMatchMode(constant($this->conf['match_mode']));
这会将配置文件中的字符串转换为常量,一切正常。当我尝试这样做时,棘手的部分开始于python:
self.sphinx.SetMatchMode(self.config['match_mode'])
我明白了:
AssertionError in
assert(mode in [SPH_MATCH_ALL, SPH_MATCH_ANY, SPH_MATCH_PHRASE, SPH_MATCH_BOOLEAN, SPH_MATCH_EXTENDED, SPH_MATCH_FULLSCAN, SPH_MATCH_EXTENDED2])
在这种情况下,输入应该是一个整数,但输入是一个字符串,我无法转换它,因为我得到一个异常 - 字符串是SPH_MATCH_ALL
。
invalid literal for int() with base 10: 'SPH_MATCH_ALL'
当我尝试这个时:
print type(self.config['match_mode']) # -- string
print type(SPH_MATCH_ALL) # -- integer
print SPH_MATCH_ALL # -- 1
print SPH_MATCH_ANY # -- 0
所以我的问题是,如何将字符串转换为整数或其认为的整数,所以我不会得到断言错误。当然,我可以做一些if / else语句,但我不想那样做。有没有优雅的方法来做到这一点?
答案 0 :(得分:3)
Python没有直接等效的PHP constant()
函数。如果有问题的常量是从模块导入的,那么最简单的方法就是这样:
import myconstants
num = int(getattr(myconstants, self.config['match_mode']))
或者如果它在当前模块中的全局范围内定义,则可以执行以下操作:
X = 1
num = int(globals()['X'])
无论哪种方式,您都可以通过让用户控制代码处理哪些对象来做一些有点冒险的事情。它不是eval()
,但它在这条道路上走了一段路。这就是我在那里包含int()
转换的原因 - 如果用户使用不是整数的名称配置系统,它们应该会失败。可能有更强大的方法来做到这一点 - 我对它不太满意,但它在某个地方接近你的PHP constant()
代码而没有完全重写。
答案 1 :(得分:1)
我不熟悉狮身人面像,但基于你的问题,我会尝试这样的事情
DEFAULT = 0
mode = getattr(self.sphinx, self.config['match_mode'], DEFAULT)
self.sphinx.SetMatchMode(mode)
假设sphinx模块以
的形式定义模式SPH_MATCH_ANY = 0
SPH_MATCH_ALL = 1
# ....
答案 2 :(得分:0)
编写一个将模式字符串转换为相应整数的函数,然后在调用config时使用它:
self.sphinx.SetMatchMode(modeToInt(self.config['match_mode']))
如果函数需要/其他丑陋,你可以躲开。