格式化或简化 Python 中的长布尔表达式?

Format or Simplify a Long Boolean Expression in Python?

我正在寻找一些想法来尽可能保持以下 Python 函数的可读性。

该函数来自 pytest conftest.py 文件。它在目录中查找文件名对,并且 cvcorpus_docxcvcorpus_expected 在测试中用作固定装置,将 运行 每对测试一次。

def pytest_generate_tests(metafunc):
    if 'cvcorpus_docx' in metafunc.fixturenames and 'cvcorpus_expected' in metafunc.fixturenames:
        actual_expected = cv_testcorpus_actual_expected()
        metafunc.parametrize("cvcorpus_docx,cvcorpus_expected", actual_expected)

根据 Python 风格指南 (PEP8),我可以看到您可能采用的多种方式。我正在与一位在 Python 方面没有经验的有能力的 C# 开发人员一起工作,我们正在开发一个小型内部 API。我希望他能够轻松快速地阅读代码。

我们中间的 Pythonistas 会保留上面的代码,并保持 98 个字符长吗?或者使用反斜杠跨行分隔 if

def pytest_generate_tests2a(metafunc):
    if 'cvcorpus_docx' in metafunc.fixturenames and \
          'cvcorpus_expected' in metafunc.fixturenames:
        actual_expected = cv_testcorpus_actual_expected()
        metafunc.parametrize("cvcorpus_docx,cvcorpus_expected", actual_expected)

或者你会把大布尔表达式括起来这样你就不需要反斜杠了吗?

def pytest_generate_tests2b(metafunc):
    if ('cvcorpus_docx' in metafunc.fixturenames and
          'cvcorpus_expected' in metafunc.fixturenames):
        actual_expected = cv_testcorpus_actual_expected()
        metafunc.parametrize("cvcorpus_docx,cvcorpus_expected", actual_expected)

2a2b 会混淆缩进吗?

或者您会采用更实用的方法并避免排长队:

def pytest_generate_tests3(metafunc):
    ae_pair = ('cvcorpus_docx', 'cvcorpus_expected')
    if all(ae in metafunc.fixturenames for ae in ae_pair):
        actual_expected = cv_testcorpus_actual_expected()
        metafunc.parametrize(','.join(ae_pair), actual_expected)

在某些方面,这看起来是最整洁的,但我不确定它是否是最易读的。

我已经看了这段代码一段时间了,想知道使用哪个(或 是否有我没见过的更好的主意。)我真的很想知道你会如何推理这种情况。

这是我最终决定做的,在代码中使用"telling the story"的Clean Code原则。请注意,它违反了 DRY(不要重复自己)规则,但这是有充分理由的。我认为这比我的其他示例更具可读性。

def pytest_generate_tests(metafunc):
    docx_fixture = 'cvcorpus_docx' in metafunc.fixturenames
    expected_fixture = 'cvcorpus_expected' in metafunc.fixturenames
    if docx_fixture and expected_fixture:
        actual_expected = cv_testcorpus_actual_expected_pairs()
        metafunc.parametrize("cvcorpus_docx,cvcorpus_expected", actual_expected)