【问题标题】:Optimal realization of cleaning the names function清理名字功能的优化实现
【发布时间】:2021-01-24 09:52:08
【问题描述】:

我想问你最好的功能性能。
我有一个清理名称的功能,它贯穿熊猫数据框列,其中每个元素都是一个长字符串。函数检查字符串是否以返回 x 的东西开头,如果 str 包含返回 y 的东西等。 我有很多这样的条件(20-30 elifs),具有不同的正则表达式清理结构(每个正则表达式取决于名称的外观):
def lets_make_a_short_name(row):
    name = row['name']
    short_name =0
    if name.startswith('something'): short_name = 'something'
    elif (name.startswith('something') or name.startswith('something')):
          short_name = re.search('(?<=_)[^_]+(?=_)',name).group()
    ....
    else: short_name = 'something'
return short_name

什么会给我最好的表现:

conditions = [df['bruto'] / df['age'] > 100, 
(df['bruto'] / df['age'] <= 100) & (df['bruto'] / df['age'] > 50), (df['bruto'] / df['age'] < 50) & 
(df['bruto'] / df['age'] > 0)]
outputs = ['high salary', 'medium salary', 'low salary']
df['salary_age_relation'] = np.select(conditions, outputs, 'no salary')
  • 或者别的什么?

提前致谢!

【问题讨论】:

  • 在不了解所有情况和结果的情况下,很难给出建议。不过,20-30 的条件似乎有点极端?
  • 我同意上面的评论,但我认为通常使用字典之类的东西作为案例切换器会击败 if else 语句

标签: python pandas function dataframe


【解决方案1】:

为了模拟一个 switch 语句,我通常定义一个这样的辅助函数:

def switch(v): yield lambda *c: v in c

可以与一次性for循环一起使用:

x = 3
for case in switch(x):
    if case(1): print("once"); break
    if case(2): print("twice"); break
else: print(x,"times")

可以定义一个变体来匹配正则表达式,而不是仅仅在列表中查找值:

def reSwitch(v): yield lambda *c: any(re.match(p,v) for p in c)

然后你可以这样写你的代码:

for case in reSwitch(name):

    if case("^something"): 
        short_name = 'something'
        break

    if case("^something","something$"):
        short_name = re.search('(?<=_)[^_]+(?=_)',name).group()
        break
    ...
else: short_name = 'something'

这不会使您的代码更短,但它肯定会更清晰和可维护。

【讨论】:

    猜你喜欢
    • 2016-11-17
    • 1970-01-01
    • 2023-03-06
    • 2018-08-01
    • 2011-07-11
    • 2018-08-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多