标签归档:pylint

为什么pylint反对单字符变量名?

问题:为什么pylint反对单字符变量名?

我仍然习惯于使用python约定并使用pylint使我的代码更具pythonic风格,但是我对pylint不喜欢单字符变量名感到困惑。我有几个这样的循环:

for x in x_values:
   my_list.append(x)

当我运行时pylint,我得到Invalid name "x" for type variable (should match [a-z_][a-z0-9_]{2,30}-这表明一个有效的变量名长度必须在3到31个字符之间,但是我浏览了PEP8命名约定,但没有看到任何有关单个小写字母的明确信息,我确实看到了很多使用它们的示例。

在PEP8中我缺少什么还是这是pylint特有的标准?

I’m still getting used to python conventions and using pylint to make my code more pythonic, but I’m puzzled by the fact that pylint doesn’t like single character variable names. I have a few loops like this:

for x in x_values:
   my_list.append(x)

and when I run pylint, I’m getting Invalid name "x" for type variable (should match [a-z_][a-z0-9_]{2,30} — that suggests that a valid variable name must be between 3 and 31 characters long, but I’ve looked through the PEP8 naming conventions and I don’t see anything explicit regarding single lower case letters, and I do see a lot of examples that use them.

Is there something I’m missing in PEP8 or is this a standard that is unique to pylint?


回答 0

PyLint不仅检查PEP8建议。它也有自己的建议,其中之一就是变量名应具有描述性且不能太短。

您可以使用它来避免这样的短名称:

my_list.extend(x_values)

或调整PyLint的配置,以告诉PyLint什么变量名是好的。

PyLint checks not only PEP8 recommendations. It has also its own recommendations, one of which is that a variable name should be descriptive and not too short.

You can use this to avoid such short names:

my_list.extend(x_values)

Or tweak PyLint’s configuration to tell PyLint what variable name are good.


回答 1

关于格尼alex所指出的内容的更多详细信息:您可以告诉PyLint为变量名(即使您少于三个字符)清楚地将变量名(您发誓发誓)作exceptions。在标题下找到或添加到您的pylintrc文件中[FORMAT]

# Good variable names which should always be accepted, separated by a comma
good-names=i,j,k,ex,Run,_,pk,x,y

这里pk(用于主键),x和y是我添加的变量名。

A little more detail on what gurney alex noted: you can tell PyLint to make exceptions for variable names which (you pinky swear) are perfectly clear even though less than three characters. Find in or add to your pylintrc file, under the [FORMAT] header:

# Good variable names which should always be accepted, separated by a comma
good-names=i,j,k,ex,Run,_,pk,x,y

Here pk (for primary key), x, and y are variable names i’ve added.


回答 2

在强类型语言中,1个字母的名称变量可能没问题,因为通常会在变量的声明中或函数/方法原型中获得名称旁边的类型:

bool check_modality(string a, Mode b, OptionList c) {
    ModalityChecker v = build_checker(a, b);
    return v.check_option(c);
}

在Python中,您不会获得此信息,因此,如果您编写:

def check_modality(a, b, c):
    v = build_checker(a, b)
    return v.check_option(c)

对于该功能可以做什么,如何调用以及返回什么,您绝对不会给维护团队提供任何线索。因此,在Python中,您倾向于使用描述性名称:

def check_modality(name, mode, option_list):
    checker = build_checker(name, mode)
    return checker.check_option(option_list)

您甚至可以添加一个文档字符串来说明这些东西的作用以及期望的类型。

In strongly typed languages, 1 letter name variables can be ok-ish, because you generally get the type next to the name in the declaration of the variable or in the function / method prototype:

bool check_modality(string a, Mode b, OptionList c) {
    ModalityChecker v = build_checker(a, b);
    return v.check_option(c);
}

In Python, you don’t get this information, so if you write:

def check_modality(a, b, c):
    v = build_checker(a, b)
    return v.check_option(c)

you’re leaving absolutely no clue for the maintenance team as to what the function could be doing, and how it is called, and what it returns. So in Python, you tend to use descriptive names:

def check_modality(name, mode, option_list):
    checker = build_checker(name, mode)
    return checker.check_option(option_list)

and you even add a docstring explaining what the stuff does and what types are expected.


回答 3

如今,还有一个选项可以覆盖正则表达式。即,如果您想允许单个字符作为变量:

pylint --variable-rgx="[a-z0-9_]{1,30}$" <filename>

因此,pylint将与PEP8相匹配,并且不会带来其他违规行为。您也可以将其添加到中.pylintrc

Nowadays there is also a option to override regexp. I.e. if you want to allow single characters as variables:

pylint --variable-rgx="[a-z0-9_]{1,30}$" <filename>

So, pylint will match PEP8 and will not bring additional violations on top. Also you can add it to .pylintrc.


回答 4

更深层次的原因是,你可能还记得你的原意abcxy,和z是指当你写你的代码,但是当别人读它,甚至当你回到你的代码,代码变得更加可读当你给它是一个语义名称。我们不会在黑板上写东西然后再擦除它。我们正在编写的代码可能会存在十年或更长时间,并且会被阅读很多次。

使用语义名称。我使用语义的名称一直喜欢ratiodenominatorobj_generatorpath,等这可能需要额外的两秒钟他们打出来,但是你节省试图找出你所写的,甚至一半,然后一小时的时间是值得的。

The deeper reason is that you may remember what you intended a, b, c, x, y, and z to mean when you wrote your code, but when others read it, or even when you come back to your code, the code becomes much more readable when you give it a semantic name. We’re not writing stuff once on a chalkboard and then erasing it. We’re writing code that might stick around for a decade or more, and be read many, many times.

Use semantic names. Semantic names I’ve used have been like ratio, denominator, obj_generator, path, etc. It may take an extra second or two to type them out, but the time you save trying to figure out what you wrote even half an hour from then is well worth it.


pylint的“公开方法太少”消息是什么意思

问题:pylint的“公开方法太少”消息是什么意思

我在某些代码上运行pylint,并收到错误“公共方法太少(0/2)”。此消息是什么意思?该pylint的文档也没有什么帮助:

当类的公共方法太少时使用,因此请确保它确实值得。

I’m running pylint on some code, and receiving the error “Too few public methods (0/2)”. What does this message mean? The pylint docs are not helpful:

Used when class has too few public methods, so be sure it’s really worth it.


回答 0

该错误基本上表明类并不意味着存储数据,因为您基本上将类视为字典。类至少应具有几种方法来处理它们所保存的数据。

如果您的Class看起来像这样:

class MyClass(object):
    def __init__(self, foo, bar):
        self.foo = foo
        self.bar = bar

考虑使用字典或namedtuple替代字典。尽管如果一堂课似乎是最好的选择,请使用它。pylint并不总是知道什么是最好的。

请注意,这namedtuple是不可变的,实例化时分配的值以后不能修改。

The error basically says that classes aren’t meant to just store data, as you’re basically treating the class as a dictionary. Classes should have at least a few methods to operate on the data that they hold.

If your class looks like this:

class MyClass(object):
    def __init__(self, foo, bar):
        self.foo = foo
        self.bar = bar

Consider using a dictionary or a namedtuple instead. Although if a class seems like the best choice, use it. pylint doesn’t always know what’s best.

Do note that namedtuple is immutable and the values assigned on instantiation cannot be modified later.


回答 1

如果您要扩展类,那么我的建议是系统地禁用此警告并继续进行,例如,在Celery任务中:

class MyTask(celery.Task):  # pylint: disable=too-few-public-methods                                                                                   
    """base for My Celery tasks with common behaviors; extends celery.Task

    ...             

即使仅扩展单个函数,您也绝对需要一个类来使该技术起作用,并且扩展绝对比黑客第三方类更好!

If you are extending a class, then my suggestion is to systematically disable this warning and move on, e.g., in the case of Celery tasks:

class MyTask(celery.Task):  # pylint: disable=too-few-public-methods                                                                                   
    """base for My Celery tasks with common behaviors; extends celery.Task

    ...             

Even if you are only extending a single function, you definitely need a class to make this technique function, and extending is definitely better than hacking on the third-party classes!


回答 2

这是pylint的盲目规则的另一种情况。

“类并不意味着存储数据”-这是一个错误的陈述。字典并不能满足所有需求。类的数据成员是有意义的,字典项是可选的。证明:您可以dictionary.get('key', DEFAULT_VALUE)防止KeyError,但__getattr__默认情况下不简单。

编辑-使用结构的推荐方法

我需要更新我的答案。现在-如果需要a struct,则有两个不错的选择:

a)只需使用 attrs

这些是为此的库:

https://www.attrs.org/en/stable/

import attr

@attr.s
class MyClass(object):  # or just MyClass: for Python 3
    foo = attr.ib()
    bar = attr.ib()

您得到的额外好处是:不编写构造函数,默认值,验证__repr__,只读对象(namedtuples即使在Python 2中也要替换),等等。

b)使用dataclasses(Py 3.7+)

根据hwjp的评论,我还建议 dataclasses

https://docs.python.org/3/library/dataclasses.html

这几乎和 attrs,并且是标准的库机制(“包含电池”),没有额外的依赖关系,但Python 3.7+除外。

上一个答案的其余部分

NamedTuple并不是很好-特别是在python 3之前typing.NamedTuplehttps : //docs.python.org/3/library/typing.html#typing.NamedTuple- 您一定要检查“从NamedTuple模式”。namedtuples从字符串描述创建的Python 2 丑陋,糟糕,并且“在字符串文字中编程”是愚蠢的。

我同意两个当前的答案(“考虑使用其他东西,但是pylint并不总是正确的” –接受的答案,以及“使用pylint抑制评论”),但是我有自己的建议。

让我再指出一次:一些类意味着 用于存储数据。

现在还要考虑的选项-使用property-ies。

class MyClass(object):
    def __init__(self, foo, bar):
        self._foo = foo
        self._bar = bar

    @property
    def foo(self):
        return self._foo

    @property
    def bar(self):
        return self._bar

在上面,您具有只读属性,对于Value Object来说,这是可以的(例如,像域驱动设计中的属性),但是您也可以提供setter-这样,您的类将能够对自己拥有的字段负责进行一些验证等。(如果有设置器,则可以在构造函数中使用它们进行赋值,即self.foo = foo代替Direct self._foo = foo,但要小心,设置器可能会假定其他字段已经初始化,然后需要在构造函数中进行自定义验证) 。

This is another case of pylint‘s blind rules.

“Classes are not meant to store data” – this is a false statement. Dictionaries are not good for everything. A data member of a class is something meaningful, a dictionary item is something optional. Proof: you can do dictionary.get('key', DEFAULT_VALUE) to prevent a KeyError, but there is no simple __getattr__ with default.

EDIT – recommended ways for using structs

I need to update my answer. Right now – if you need a struct, you have two great options:

a) Just use attrs

These is a library for that:

https://www.attrs.org/en/stable/

import attr

@attr.s
class MyClass(object):  # or just MyClass: for Python 3
    foo = attr.ib()
    bar = attr.ib()

What you get extra: not writing constructors, default values, validation, __repr__, read-only objects (to replace namedtuples, even in Python 2) and more.

b) Use dataclasses (Py 3.7+)

Following hwjp’s comment, I also recommend dataclasses:

https://docs.python.org/3/library/dataclasses.html

This is almost as good as attrs, and is a standard library mechanism (“batteries included”), with no extra dependencies, except Python 3.7+.

Rest of Previous answer

NamedTuple is not great – especially before python 3’s typing.NamedTuple: https://docs.python.org/3/library/typing.html#typing.NamedTuple – you definitely should check out the “class derived from NamedTuple” pattern. Python 2 – namedtuples created from string descriptions – is ugly, bad and “programming inside string literals” stupid.

I agree with the two current answers (“consider using something else, but pylint isn’t always right” – the accepted one, and “use pylint suppressing comment”), but I have my own suggestion.

Let me point this out one more time: Some classes are meant just to store data.

Now the option to also consider – use property-ies.

class MyClass(object):
    def __init__(self, foo, bar):
        self._foo = foo
        self._bar = bar

    @property
    def foo(self):
        return self._foo

    @property
    def bar(self):
        return self._bar

Above you have read-only properties, which is OK for Value Object (e.g. like those in Domain Driven Design), but you can also provide setters – this way your class will be able to take responsibility for the fields which you have – for example to do some validation etc. (if you have setters, you can assign using them in the constructor, i.e. self.foo = foo instead of direct self._foo = foo, but careful, the setters may assume other fields to be initialized already, and then you need custom validation in the constructor).


回答 3

当老板期望单一责任原则时,这很困难,但皮林特拒绝了。因此,请向您的Class添加第二种方法,以使您的Class违反单一责任原则。在旁观者的眼中,您打算采取多大责任的原则。

我的解决办法

我在类中添加了一个额外的方法,因此它现在可以完成两件事。

def __str__(self):
    return self.__class__.__name__

我只是想知道我是否现在需要将我的Class分成2个单独的文件,也许还有模块。

问题得到了解决,但我的同事们却没有花一整天的时间讨论规范,而不是像生死攸关的问题那样坚持下去。

It’s hard when your boss expects single responsibility principle, but pylint says no. So add a second method to your class so your class violates single responsibility principle. How far you are meant to take single responsibility principle is in the eye the beholder.

My fix,

I added an extra method to my class, so it now does 2 things.

def __str__(self):
    return self.__class__.__name__

I’m just wondering if I need to split my class into 2 separate files now, and maybe modules aswell.

problem solved, but not with my colleagues who spend all day arguing the spec, rather than getting on with it, like it’s life and death.


如何在Pylint的文件级别禁用“缺少文档字符串”警告?

问题:如何在Pylint的文件级别禁用“缺少文档字符串”警告?

Pylint引发错误,指出某些文件缺少文档字符串。我尝试为每个类,方法和函数添加docstring,但是Pylint似乎还在检查文件的开头是否应该有docstring。我可以以某种方式禁用它吗?我想在类,函数或方法中缺少文档字符串的通知,但对于具有文档字符串的文件,这不是强制性的。

(是否在专有源文件的开头经常出现法律术语?是否有任何示例?我不知道单独发布这样一个琐碎的问题是否可以。)

Pylint throws errors that some of files are missing docstrings. I try and add docstrings to each class, method and function but it seems that Pylint also checks that files should a docstring at the beginning of it. Can i disable this somehow? I would like to be notified of a docstring is missing inside a class, function or method but it shouldn’t be mandatory for a file to have a docstring.

(Is there a term of the legal jargon often found at the beginning of a proprietary source file? Any examples? I don’t know whether it is a okay to post such a trivial question separately.)


回答 0

Python模块最好有一个文档字符串,解释该模块的功能,提供的内容以及使用类的示例。这与您在提供版权和许可信息的文件开头经常看到的注释不同,IMO不应在文档字符串中添加注释(有些人甚至认为它们应该完全消失,请参见例如http:// hackerboss。 com / get-rid-of-templates /

在pylint 2.4及更高版本中,您可以missing-docstring通过使用以下三个子消息来区分各种类型:

  • C0114missing-module-docstring
  • C0115missing-class-docstring
  • C0116missing-function-docstring

因此以下.pylintrc文件应该工作:

[MASTER]
disable=
    C0114, # missing-module-docstring

对于以前的Pylint版本,它没有针对文档字符串可能出现的各个位置的单独代码,因此您只能禁用C0111。问题是,如果您在模块范围内禁用此功能,那么它将在模块中的所有位置都被禁用(即,由于缺少函数/类/方法文档字符串,您将不会得到任何C行。这可能不太好。

因此,我建议添加一个小的缺少的文档字符串,例如:

"""
high level support for doing this and that.
"""

很快,您将发现有用的东西,例如提供一些示例,说明如何使用模块的各种类/函数,这些类/函数不一定属于类/函数的各个文档字符串(例如这些互动或类似的快速入门指南)。

It is nice for a Python module to have a docstring, explaining what the module does, what it provides, examples of how to use the classes. This is different from the comments that you often see at the beginning of a file giving the copyright and license information, which IMO should not go in the docstring (some even argue that they should disappear altogether, see eg. http://hackerboss.com/get-rid-of-templates/)

With pylint 2.4 and above you can differentiate between the various missing-docstring by using the three following sub-messages:

  • C0114 (missing-module-docstring)
  • C0115 (missing-class-docstring)
  • C0116 (missing-function-docstring)

So the following .pylintrc file should work:

[MASTER]
disable=
    C0114, # missing-module-docstring

For previous versions of Pylint, it does not have a separate code for the various place where docstrings can occur, so all you can do is disable C0111. The problem is that if you disable this at module scope, then it will be disabled everywhere in the module (i.e you won’t get any C line for missing function / class / method docstring. Which arguably is not nice.

So what I suggest is adding that small missing docstring, saying something like:

"""
high level support for doing this and that.
"""

Soon enough, you’ll be finding useful things to put in there, such as providing examples of how to use the various classes / functions of the module which do not necessarily belong to the individual docstrings of the classes / functions (such as how these interact, or something like a quick start guide).


回答 1

已经很晚了,但我仍然觉得它很有用。所以分享。在这里找到这个。

您可以为pylint添加“ –errors-only”标志,以禁用警告。

为此,请转到设置。编辑以下行:

"python.linting.pylintArgs": []

"python.linting.pylintArgs": ["--errors-only"]

而且你很好!

It’s late, but still I found it useful. So sharing. Found this here.

You can add “–errors-only” flag for pylint to disable warnings.

To do this, go to settings. Edit the following line:

"python.linting.pylintArgs": []

As

"python.linting.pylintArgs": ["--errors-only"]

And you are good to go!


回答 2

我认为在不禁用此功能的情况下,修复相对容易。

def kos_root():
    """Return the pathname of the KOS root directory."""
    global _kos_root
    if _kos_root: return _kos_root

您需要做的就是在每个函数中添加三重双引号字符串。

I think the fix is relative easy without disabling this feature.

def kos_root():
    """Return the pathname of the KOS root directory."""
    global _kos_root
    if _kos_root: return _kos_root

All you need to do is add the triple double quotes string in every function.


回答 3

我来找答案是因为,正如@cerin所说,在Django项目中,向django在创建新应用时自动生成的每个文件中添加模块文档字符串是麻烦且多余的。

因此,作为pylint不允许您指定文档字符串类型不同的事实的解决方法,您可以执行以下操作:

pylint */*.py --msg-template='{path}: {C}:{line:3d},{column:2d}: {msg}' | grep docstring | grep -v module

您必须更新msg-template,以便在grep时仍会知道文件名。这将返回除模块以外的所有其他缺少文档字符串类型。

然后,您可以修复所有这些错误,然后运行:

pylint */*.py --disable=missing-docstring

I came looking for an answer because, as @cerin said, in Django projects it is cumbersome and redundant to add module docstrings to every one of the files that django automatically generates when creating a new app.

So, as a workaround for the fact that pylint doesn’t let you specify a difference in docstring types, you can do this:

pylint */*.py --msg-template='{path}: {C}:{line:3d},{column:2d}: {msg}' | grep docstring | grep -v module

You have to update the msg-template so that when you grep you will still know the file name. This returns all the other missing-docstring types excluding modules.

Then you can fix all of those errors, and afterwards just run:

pylint */*.py --disable=missing-docstring

回答 4

。Pylint当前不允许您区分文档字符串警告。

但是,您可以将flake8用于所有python代码检查以及doc-string扩展名,以忽略此警告。

使用pip安装doc字符串扩展名(内部使用pydocstyle)。

pip install flake8_docstrings

然后,您可以只使用--ignore D100开关。例如flake8 file.py --ignore D100

No. Pylint doesn’t currently let you discriminate between doc-string warnings.

However, you can use flake8 for all python code checking along with the doc-string extension to ignore this warning.

Install the doc-string extension with pip (Internally, It uses pydocstyle).

pip install flake8_docstrings

You can then just use the --ignore D100 switch. For example flake8 file.py --ignore D100


回答 5

只需将以下行放在要禁用这些警告的任何文件的开头。

# pylint: disable=missing-module-docstring
# pylint: disable=missing-class-docstring
# pylint: disable=missing-function-docstring

Just put the following lines at the beginning of any file you want to disable these warnings.

# pylint: disable=missing-module-docstring
# pylint: disable=missing-class-docstring
# pylint: disable=missing-function-docstring

回答 6

在pylint 2.4及更高版本中,您可以missing-docstring通过使用以下三个子消息来区分各种类型:

  • C0114missing-module-docstring
  • C0115missing-class-docstring
  • C0116missing-function-docstring

因此以下.pylintrc文件应该工作:

[MASTER]
disable=
    C0114, # missing-module-docstring

With pylint 2.4 and above you can differentiate between the various missing-docstring by using the three following sub-messages:

  • C0114 (missing-module-docstring)
  • C0115 (missing-class-docstring)
  • C0116 (missing-function-docstring)

So the following .pylintrc file should work:

[MASTER]
disable=
    C0114, # missing-module-docstring

回答 7

编辑“ C:\ Users \您的User \ AppData \ Roaming \ Code \ User \ settings.json”,并将这些python.linting.pylintArgs行添加到末尾,如下所示:

{
    "team.showWelcomeMessage": false,
    "python.dataScience.sendSelectionToInteractiveWindow": true,
    "git.enableSmartCommit": true,
    "powershell.codeFormatting.useCorrectCasing": true,
    "files.autoSave": "onWindowChange",
    "python.linting.pylintArgs": [
        "--load-plugins=pylint_django",
        "--errors-only"
    ],
}

Edit “C:\Users\Your User\AppData\Roaming\Code\User\settings.json” and add these python.linting.pylintArgs lines at the end as shown below:

{
    "team.showWelcomeMessage": false,
    "python.dataScience.sendSelectionToInteractiveWindow": true,
    "git.enableSmartCommit": true,
    "powershell.codeFormatting.useCorrectCasing": true,
    "files.autoSave": "onWindowChange",
    "python.linting.pylintArgs": [
        "--load-plugins=pylint_django",
        "--errors-only"
    ],
}

回答 8

(1)CTRL + SHIFT + P(2)然后键入并单击> preferences:配置特定于语言的设置(3),然后在代码后键入python

{
"python.linting.pylintArgs": [
    "--load-plugins=pylint_django","--errors-only"
],

}

(1) CTRL+SHIFT+P (2)Then type and click on >preferences:configure language specific settings (3)and then type python after that past the code

{
"python.linting.pylintArgs": [
    "--load-plugins=pylint_django","--errors-only"
],

}

回答 9

就我而言,使用pylint 2.6.0,即使显式禁用了missing-module-docstringmissing-class-docstring并且missing-function-docstring在我的.pylintrc文件中,丢失的docstring消息也不会消失。最后,以下配置对我有用:

[MESSAGES CONTROL]

disable=missing-docstring,empty-docstring

显然,除非同时禁用两个检查,否则pylint 2.6.0仍将验证文档字符串。

In my case, with pylint 2.6.0, the missing docstring messages wouldn’t disappear, even after explicitly disabling missing-module-docstring, missing-class-docstring and missing-function-docstring in my .pylintrc file. Finally, the following configuration worked for me:

[MESSAGES CONTROL]

disable=missing-docstring,empty-docstring

Apparently, pylint 2.6.0 still validates docstrings unless both checks are disabled.


回答 10

转到“ settings.json”并禁用python pydocstyle

"python.linting.pydocstyleEnabled": false

Go to “settings.json” and disable python pydocstyle

"python.linting.pydocstyleEnabled": false

PyLint“无法导入”错误-如何设置PYTHONPATH?

问题:PyLint“无法导入”错误-如何设置PYTHONPATH?

我正在Windows的Wing IDE中运行PyLint。我的项目中有一个子目录(程序包),在程序包中,我从顶层(即)导入模块。

__init__.py
myapp.py
one.py
subdir\
    __init__.py
    two.py

two.py我的内部import one,这在运行时效果很好,因为顶层目录(从中myapp.py运行)位于Python路径中。但是,当我在two.py上运行PyLint时,出现了一个错误:

F0401: Unable to import 'one'

我该如何解决?

I’m running PyLint from inside Wing IDE on Windows. I have a sub-directory (package) in my project and inside the package I import a module from the top level, ie.

__init__.py
myapp.py
one.py
subdir\
    __init__.py
    two.py

Inside two.py I have import one and this works fine at runtime, because the top-level directory (from which myapp.py is run) is in the Python path. However, when I run PyLint on two.py it gives me an error:

F0401: Unable to import 'one'

How do I fix this?


回答 0

我知道有两个选择。

一,更改PYTHONPATH环境变量,使其包含模块上方的目录。

或者,编辑~/.pylintrc以包括模块上方的目录,如下所示:

[MASTER]
init-hook='import sys; sys.path.append("/path/to/root")'

(或者在其他版本的pylint中,init-hook要求您将[General]更改为[MASTER])

这两个选项都应该起作用。

希望有帮助。

There are two options I’m aware of.

One, change the PYTHONPATH environment variable to include the directory above your module.

Alternatively, edit ~/.pylintrc to include the directory above your module, like this:

[MASTER]
init-hook='import sys; sys.path.append("/path/to/root")'

(Or in other version of pylint, the init-hook requires you to change [General] to [MASTER])

Both of these options ought to work.

Hope that helps.


回答 1

更改路径的解决方案init-hook很好,但是我不喜欢必须在此处添加绝对路径的事实,因此,我无法在项目开发人员之间共享此pylintrc文件。这种使用相对路径指向pylintrc文件的解决方案对我来说效果更好:

[MASTER]
init-hook="from pylint.config import find_pylintrc; import os, sys; sys.path.append(os.path.dirname(find_pylintrc()))"

请注意,pylint.config.PYLINTRC该值也存在,并且具有与相同的值find_pylintrc()

The solution to alter path in init-hook is good, but I dislike the fact that I had to add absolute path there, as result I can not share this pylintrc file among the developers of the project. This solution using relative path to pylintrc file works better for me:

[MASTER]
init-hook="from pylint.config import find_pylintrc; import os, sys; sys.path.append(os.path.dirname(find_pylintrc()))"

Note that pylint.config.PYLINTRC also exists and has the same value as find_pylintrc().


回答 2

1)sys.path是一个列表。

2)问题有时是sys.path不是您的virtualenv.path,并且您想在virtualenv中使用pylint

3)像这样说,使用init-hook(注意’和’pylint的解析是严格的)

[Master]
init-hook='sys.path = ["/path/myapps/bin/", "/path/to/myapps/lib/python3.3/site-packages/", ... many paths here])'

要么

[Master]
init-hook='sys.path = list(); sys.path.append("/path/to/foo")'

..和

pylint --rcfile /path/to/pylintrc /path/to/module.py

1) sys.path is a list.

2) The problem is sometimes the sys.path is not your virtualenv.path and you want to use pylint in your virtualenv

3) So like said, use init-hook (pay attention in ‘ and ” the parse of pylint is strict)

[Master]
init-hook='sys.path = ["/path/myapps/bin/", "/path/to/myapps/lib/python3.3/site-packages/", ... many paths here])'

or

[Master]
init-hook='sys.path = list(); sys.path.append("/path/to/foo")'

.. and

pylint --rcfile /path/to/pylintrc /path/to/module.py

回答 3

可以通过在venv下配置pylint路径来解决该问题:$ cat .vscode / settings.json

{
    "python.pythonPath": "venv/bin/python",
    "python.linting.pylintPath": "venv/bin/pylint"
}

The problem can be solved by configuring pylint path under venv: $ cat .vscode/settings.json

{
    "python.pythonPath": "venv/bin/python",
    "python.linting.pylintPath": "venv/bin/pylint"
}

回答 4

您是否__init__.py在两个目录中都有一个空文件来让python知道dirs是模块?

当您不在文件夹中运行时(例如,虽然不是我使用过的pylint),其基本轮廓是:

topdir\
  __init__.py
  functions_etc.py
  subdir\
    __init__.py
    other_functions.py

这是怎样的Python解释器知道不参考当前目录中的模块,因此,如果pylint的是从自身的绝对路径运行它就能访问functions_etc.pytopdir.functions_etctopdir.subdir.other_functions,只要topdir是对的PYTHONPATH

更新:如果问题不在于__init__.py文件,也许只是尝试将模块复制或移动到c:\Python26\Lib\site-packages-这是放置其他软件包的常见位置,并且肯定会在pythonpath上。如果您知道如何执行Windows符号链接或等效链接(我不知道!),则可以这样做。这里还有更多选项:http://docs.python.org/install/index.html,包括在开发代码的用户级目录后附加sys.path的选项,但实际上,我通常只是象征性地链接我将本地开发目录复制到站点软件包-将其复制具有相同的效果。

Do you have an empty __init__.py file in both directories to let python know that the dirs are modules?

The basic outline when you are not running from within the folder (ie maybe from pylint’s, though I haven’t used that) is:

topdir\
  __init__.py
  functions_etc.py
  subdir\
    __init__.py
    other_functions.py

This is how the python interpreter is aware of the module without reference to the current directory, so if pylint is running from its own absolute path it will be able to access functions_etc.py as topdir.functions_etc or topdir.subdir.other_functions, provided topdir is on the PYTHONPATH.

UPDATE: If the problem is not the __init__.py file, maybe just try copying or moving your module to c:\Python26\Lib\site-packages — that is a common place to put additional packages, and will definitely be on your pythonpath. If you know how to do Windows symbolic links or the equivalent (I don’t!), you could do that instead. There are many more options here: http://docs.python.org/install/index.html, including the option of appending sys.path with the user-level directory of your development code, but in practice I usually just symbolically link my local development dir to site-packages – copying it over has the same effect.


回答 5

我在此页面上找到的关于此问题的一般答案请不要打开,网站显示错误

创建.pylintrc并添加

[MASTER]
init-hook="from pylint.config import find_pylintrc;
import os, sys; sys.path.append(os.path.dirname(find_pylintrc()))"

general answer for this question I found on this page PLEASE NOT OPEN, SITE IS BUGED

create .pylintrc and add

[MASTER]
init-hook="from pylint.config import find_pylintrc;
import os, sys; sys.path.append(os.path.dirname(find_pylintrc()))"

回答 6

我不知道它如何与WingIDE一起使用,但是对于将PyLint与Geany一起使用,我将外部命令设置为:

PYTHONPATH=${PYTHONPATH}:$(dirname %d) pylint --output-format=parseable --reports=n "%f"

其中%f是文件名,%d是路径。可能对某人有用:)

I don’t know how it works with WingIDE, but for using PyLint with Geany, I set my external command to:

PYTHONPATH=${PYTHONPATH}:$(dirname %d) pylint --output-format=parseable --reports=n "%f"

where %f is the filename, and %d is the path. Might be useful for someone :)


回答 7

我必须更新系统PYTHONPATH变量以添加我的App Engine路径。就我而言,我只需要编辑~/.bashrc文件并添加以下行:

export PYTHONPATH=$PYTHONPATH:/path/to/google_appengine_folder

实际上,我尝试设置第init-hook一个,但这不能在我的代码库中始终解决此问题(不确定原因)。一旦将其添加到系统路径中(一般来说可能是一个好主意),我的问题就消失了。

I had to update the system PYTHONPATH variable to add my App Engine path. In my case I just had to edit my ~/.bashrc file and add the following line:

export PYTHONPATH=$PYTHONPATH:/path/to/google_appengine_folder

In fact, I tried setting the init-hook first but this did not resolve the issue consistently across my code base (not sure why). Once I added it to the system path (probably a good idea in general) my issues went away.


回答 8

我刚刚发现的一种解决方法是实际上只对整个软件包运行PyLint,而不是对单个文件运行。不知何故,它设法找到了导入的模块。

One workaround that I only just discovered is to actually just run PyLint for the entire package, rather than a single file. Somehow, it manages to find imported module then.


回答 9

尝试

if __name__ == '__main__':
    from [whatever the name of your package is] import one
else:
    import one

请注意,在Python 3中,else子句中该部分的语法为

from .. import one

再三考虑,这可能无法解决您的特定问题。我误解了这个问题,并认为two.py已作为主要模块运行,但事实并非如此。考虑到Python 2.6(不absolute_import从导入__future__)和Python 3.x处理导入的方式的差异,我认为对于Python 2.6无需这样做。

不过,如果最终您确实切换到Python 3,并计划将模块既用作包模块又用作包内的独立脚本,那么最好保留以下内容:

if __name__ == '__main__':
    from [whatever the name of your package is] import one   # assuming the package is in the current working directory or a subdirectory of PYTHONPATH
else:
    from .. import one

心里。

编辑:现在为您的实际问题提供可能的解决方案。从包含one模块的目录中运行PyLint (也许通过命令行),或者在运行PyLint时将以下代码放在某个位置:

import os

olddir = os.getcwd()
os.chdir([path_of_directory_containing_module_one])
import one
os.chdir(olddir)

基本上,作为摆弄PYTHONPATH的替代方法,只需确保当前工作目录是one.py执行导入时包含的目录。

(查看Brian的答案,您可能会将先前的代码分配给init_hook,但是如果您打算这样做,则可以简单地对其进行附加sys.path操作,这比我的解决方案要优雅得多。)

Try

if __name__ == '__main__':
    from [whatever the name of your package is] import one
else:
    import one

Note that in Python 3, the syntax for the part in the else clause would be

from .. import one

On second thought, this probably won’t fix your specific problem. I misunderstood the question and thought that two.py was being run as the main module, but that is not the case. And considering the differences in the way Python 2.6 (without importing absolute_import from __future__) and Python 3.x handle imports, you wouldn’t need to do this for Python 2.6 anyway, I don’t think.

Still, if you do eventually switch to Python 3 and plan on using a module as both a package module and as a standalone script inside the package, it may be a good idea to keep something like

if __name__ == '__main__':
    from [whatever the name of your package is] import one   # assuming the package is in the current working directory or a subdirectory of PYTHONPATH
else:
    from .. import one

in mind.

EDIT: And now for a possible solution to your actual problem. Either run PyLint from the directory containing your one module (via the command line, perhaps), or put the following code somewhere when running PyLint:

import os

olddir = os.getcwd()
os.chdir([path_of_directory_containing_module_one])
import one
os.chdir(olddir)

Basically, as an alternative to fiddling with PYTHONPATH, just make sure the current working directory is the directory containing one.py when you do the import.

(Looking at Brian’s answer, you could probably assign the previous code to init_hook, but if you’re going to do that then you could simply do the appending to sys.path that he does, which is slightly more elegant than my solution.)


回答 10

关键是在sys.path不考虑env变量的情况下将项目目录添加到其中。

对于使用VSCode的人,如果您的项目有基本目录,这是一种单线解决方案:

[MASTER]
init-hook='base_dir="my_spider"; import sys,os,re; _re=re.search(r".+\/" + base_dir, os.getcwd()); project_dir = _re.group() if _re else os.path.join(os.getcwd(), base_dir); sys.path.append(project_dir)'

让我解释一下:

  • re.search(r".+\/" + base_dir, os.getcwd()).group():根据编辑文件查找基本目录

  • os.path.join(os.getcwd(), base_dir):添加cwdsys.path满足命令行环境


仅供参考,这是我的.pylintrc:

https://gist.github.com/chuyik/f0ffc41a6948b6c87c7160151ffe8c2f

The key is to add your project directory to sys.path without considering about the env variable.

For someone who use VSCode, here’s a one-line solution for you if there’s a base directory of your project:

[MASTER]
init-hook='base_dir="my_spider"; import sys,os,re; _re=re.search(r".+\/" + base_dir, os.getcwd()); project_dir = _re.group() if _re else os.path.join(os.getcwd(), base_dir); sys.path.append(project_dir)'

Let me explain it a little bit:

  • re.search(r".+\/" + base_dir, os.getcwd()).group(): find base directory according to the editing file

  • os.path.join(os.getcwd(), base_dir): add cwd to sys.path to meet command line environment


FYI, here’s my .pylintrc:

https://gist.github.com/chuyik/f0ffc41a6948b6c87c7160151ffe8c2f


回答 11

我遇到了同样的问题,并通过在virtualenv中安装pylint,然后将.pylintrc文件添加到我的项目目录中并在文件中添加以下内容来修复了该问题:

[Master]
init-hook='sys.path = list(); sys.path.append("./Lib/site-packages/")'

I had this same issue and fixed it by installing pylint in my virtualenv and then adding a .pylintrc file to my project directory with the following in the file:

[Master]
init-hook='sys.path = list(); sys.path.append("./Lib/site-packages/")'

回答 12

也许通过在PYTHONPATH内手动附加目录?

sys.path.append(dirname)

Maybe by manually appending the dir inside the PYTHONPATH?

sys.path.append(dirname)

回答 13

我遇到了同样的问题,因为我找不到答案,所以我希望这可以帮助任何有类似问题的人。

我用飞配epylint。基本上我所做的就是添加一个dired-mode-hook,以检查dired目录是否为python软件包目录。如果是,我将其添加到PYTHONPATH。就我而言,如果目录包含名为“ setup.py”的文件,则我认为该目录是python软件包。

;;;;;;;;;;;;;;;;;
;; PYTHON PATH ;;
;;;;;;;;;;;;;;;;;

(defun python-expand-path ()
  "Append a directory to the PYTHONPATH."
  (interactive
   (let ((string (read-directory-name 
          "Python package directory: " 
          nil 
          'my-history)))
     (setenv "PYTHONPATH" (concat (expand-file-name string)
                  (getenv ":PYTHONPATH"))))))

(defun pythonpath-dired-mode-hook ()
  (let ((setup_py (concat default-directory "setup.py"))
    (directory (expand-file-name default-directory)))
    ;;   (if (file-exists-p setup_py)
    (if (is-python-package-directory directory)
    (let ((pythonpath (concat (getenv "PYTHONPATH") ":" 
                  (expand-file-name directory))))
      (setenv "PYTHONPATH" pythonpath)
      (message (concat "PYTHONPATH=" (getenv "PYTHONPATH")))))))

(defun is-python-package-directory (directory)
  (let ((setup_py (concat directory "setup.py")))
    (file-exists-p setup_py)))

(add-hook 'dired-mode-hook 'pythonpath-dired-mode-hook)

希望这可以帮助。

I had the same problem and since i could not find a answer I hope this can help anyone with a similar problem.

I use flymake with epylint. Basically what i did was add a dired-mode-hook that check if the dired directory is a python package directory. If it is I add it to the PYTHONPATH. In my case I consider a directory to be a python package if it contains a file named “setup.py”.

;;;;;;;;;;;;;;;;;
;; PYTHON PATH ;;
;;;;;;;;;;;;;;;;;

(defun python-expand-path ()
  "Append a directory to the PYTHONPATH."
  (interactive
   (let ((string (read-directory-name 
          "Python package directory: " 
          nil 
          'my-history)))
     (setenv "PYTHONPATH" (concat (expand-file-name string)
                  (getenv ":PYTHONPATH"))))))

(defun pythonpath-dired-mode-hook ()
  (let ((setup_py (concat default-directory "setup.py"))
    (directory (expand-file-name default-directory)))
    ;;   (if (file-exists-p setup_py)
    (if (is-python-package-directory directory)
    (let ((pythonpath (concat (getenv "PYTHONPATH") ":" 
                  (expand-file-name directory))))
      (setenv "PYTHONPATH" pythonpath)
      (message (concat "PYTHONPATH=" (getenv "PYTHONPATH")))))))

(defun is-python-package-directory (directory)
  (let ((setup_py (concat directory "setup.py")))
    (file-exists-p setup_py)))

(add-hook 'dired-mode-hook 'pythonpath-dired-mode-hook)

Hope this helps.


回答 14

如果有人在寻找一种方法来将Pylint作为PyCharm中的外部工具运行并使其与他们的虚拟环境一起工作(为什么我要问这个问题),那么我将通过以下方式解决它:

  1. 在PyCharm>首选项>工具>外部工具中,添加或编辑pylint的项目。
  2. 在“编辑工具”对话框的“工具设置”中,将“程序”设置为使用python解释器目录中的pylint: $PyInterpreterDirectory$/pylint
  3. 在“参数”字段中设置其他参数,例如: --rcfile=$ProjectFileDir$/pylintrc -r n $FileDir$
  4. 将工作目录设置为 $FileDir$

现在,使用pylint作为外部工具,可以在使用公共配置文件选择的任何目录上运行pylint,并使用为项目配置的任何解释器(大概是您的virtualenv解释器)。

In case anybody is looking for a way to run pylint as an external tool in PyCharm and have it work with their virtual environments (why I came to this question), here’s how I solved it:

  1. In PyCharm > Preferences > Tools > External Tools, Add or Edit an item for pylint.
  2. In the Tool Settings of the Edit Tool dialog, set Program to use pylint from the python interpreter directory: $PyInterpreterDirectory$/pylint
  3. Set your other parameters in the Parameters field, like: --rcfile=$ProjectFileDir$/pylintrc -r n $FileDir$
  4. Set your working directory to $FileDir$

Now using pylint as an external tool will run pylint on whatever directory you have selected using a common config file and use whatever interpreter is configured for your project (which presumably is your virtualenv interpreter).


回答 15

这是一个老问题,但是没有可接受的答案,所以我建议这样做:将two.py中的import语句更改为:

from .. import one

在我当前的环境(Python 3.6,使用pylint 2.3.1的VSCode)中,这清除了标记的语句。

This is an old question but has no accepted answer, so I’ll suggest this: change the import statement in two.py to read:

from .. import one

In my current environment (Python 3.6, VSCode using pylint 2.3.1) this clears the flagged statement.


回答 16

我找到了一个不错的答案。编辑您的pylintrc并在master中添加以下内容

init-hook="import imp, os; from pylint.config import find_pylintrc; imp.load_source('import_hook', os.path.join(os.path.dirname(find_pylintrc()), 'import_hook.py'))"

I found a nice answer. Edit your pylintrc and add the following in master

init-hook="import imp, os; from pylint.config import find_pylintrc; imp.load_source('import_hook', os.path.join(os.path.dirname(find_pylintrc()), 'import_hook.py'))"

回答 17

安装Python时,可以设置路径。如果已经定义了路径,那么您可以在VS Code中进行操作,按Ctrl + Shift + P并键入Python:选择“解释器”并选择Python的更新版本。请点击此链接以获取更多信息,https://code.visualstudio.com/docs/python/environments

When you install Python, you can set up the path. If path is already defined then what you can do is within VS Code, hit Ctrl+Shift+P and type Python: Select Interpreter and select updated version of Python. Follow this link for more information, https://code.visualstudio.com/docs/python/environments


回答 18

如果使用vscode,请确保您的软件包目录不在_pychache__目录中。

if you using vscode,make sure your package directory is out of the _pychache__ directory.


回答 19

如果您在Linux中使用Cython,则解决了删除module.cpython-XXm-X-linux-gnu.so项目目标目录中的文件的问题。

If you are using Cython in Linux, I resolved removing module.cpython-XXm-X-linux-gnu.so files in my project target directory.


回答 20

只需在.vscode / settings.json文件中添加此代码

,“ python.linting.pylintPath”:“ venv / bin / pylint”

这将通知pylint的位置(这是python的错误检查器)

just add this code in .vscode/settings.json file

,”python.linting.pylintPath”: “venv/bin/pylint”

This will notify the location of pylint(which is an error checker for python)


回答 21

您好,我能够从其他目录导入软件包。我只是做了以下事情:注意:我正在使用VScode

创建Python软件包的步骤使用Python软件包确实非常简单。您需要做的只是:

创建一个目录,并为其指定软件包的名称。将类放进去。在目录中创建一个初始化 .py文件

例如:您有一个名为Framework的文件夹,其中保存了所有自定义类,您的工作是在名为Framework的文件夹内创建一个init .py文件。

在导入时,您需要以这种方式导入->

从Framework导入库

因此E0401错误消失了,Framework是您刚在其中创建init .py 的文件夹,而base是您要自定义的模块,您需要将其导入并在该模块上工作,希望它能有所帮助!!!

Hello i was able to import the packages from different directory. I just did the following: Note: I am using VScode

Steps to Create a Python Package Working with Python packages is really simple. All you need to do is:

Create a directory and give it your package’s name. Put your classes in it. Create a init.py file in the directory

For example: you have a folder called Framework where you are keeping all the custom classes there and your job is to just create a init.py file inside the folder named Framework.

And while importing you need to import in this fashion—>

from Framework import base

so the E0401 error disappears Framework is the folder where you just created init.py and base is your custom module which you are required to import into and work upon Hope it helps!!!!


如何让PyLint识别numpy成员?

问题:如何让PyLint识别numpy成员?

我在Python项目上运行PyLint。PyLint抱怨无法找到numpy成员。在避免跳过成员资格检查的同时如何避免这种情况。

从代码:

import numpy as np

print np.zeros([1, 4])

运行时,我得到了预期的结果:

[[0. 0. 0. 0.]]

但是,pylint给了我这个错误:

E:3,6:模块’numpy’没有’zeros’成员(no-member)

对于版本,我使用的是pylint 1.0.0(星号1.0.1,常见的0.60.0),并尝试使用numpy 1.8.0。

I am running PyLint on a Python project. PyLint makes many complaints about being unable to find numpy members. How can I avoid this while avoiding skipping membership checks.

From the code:

import numpy as np

print np.zeros([1, 4])

Which, when ran, I get the expected:

[[ 0. 0. 0. 0.]]

However, pylint gives me this error:

E: 3, 6: Module ‘numpy’ has no ‘zeros’ member (no-member)

For versions, I am using pylint 1.0.0 (astroid 1.0.1, common 0.60.0) and trying to work with numpy 1.8.0 .


回答 0

如果将Visual Studio Code与Don Jayamanne的出色Python扩展一起使用,请将用户设置添加到numpy白名单:

{
    // whitelist numpy to remove lint errors
    "python.linting.pylintArgs": [
        "--extension-pkg-whitelist=numpy"
    ]
}

If using Visual Studio Code with Don Jayamanne’s excellent Python extension, add a user setting to whitelist numpy:

{
    // whitelist numpy to remove lint errors
    "python.linting.pylintArgs": [
        "--extension-pkg-whitelist=numpy"
    ]
}

回答 1

我这里有同样的问题,即使所有相关的软件包的最新版本(astroid 1.3.2logilab_common 0.63.2pylon 1.4.0)。

以下解决方案非常有用:在该部分中,numpy我通过修改pylintrc文件将其添加到了被忽略的模块列表中[TYPECHECK]

[TYPECHECK]

ignored-modules = numpy

根据错误,您可能还需要添加以下行(仍在中[TYPECHECK] section):

ignored-classes = numpy

I had the same issue here, even with the latest versions of all related packages (astroid 1.3.2, logilab_common 0.63.2, pylon 1.4.0).

The following solution worked like a charm: I added numpy to the list of ignored modules by modifying my pylintrc file, in the [TYPECHECK] section:

[TYPECHECK]

ignored-modules = numpy

Depending on the error, you might also need to add the following line (still in the [TYPECHECK] section):

ignored-classes = numpy

回答 2

对于正在处理的一个小numpy项目,我遇到了相同的错误,因此决定忽略numpy模块就可以了。我创建了一个.pylintrc文件:

$ pylint --generate-rcfile > ~/.pylintrc

根据paduwan和j_houg的建议,我修改了以下部分:

[MASTER]

# A comma-separated list of package or module names from where C extensions may
# be loaded. Extensions are loading into the active Python interpreter and may
# run arbitrary code
extension-pkg-whitelist=numpy

[TYPECHECK]

# List of module names for which member attributes should not be checked
# (useful for modules/projects where namespaces are manipulated during runtime
# and thus existing member attributes cannot be deduced by static analysis. It
# supports qualified module names, as well as Unix pattern matching.
ignored-modules=numpy

# List of classes names for which member attributes should not be checked
# (useful for classes with attributes dynamically set). This supports can work
# with qualified names.
ignored-classes=numpy

它“解决”了我的问题。

I was getting the same error for a small numpy project I was working on and decided that ignoring the numpy modules would do just fine. I created a .pylintrc file with:

$ pylint --generate-rcfile > ~/.pylintrc

and following paduwan’s and j_houg’s advice I modified the following sectors:

[MASTER]

# A comma-separated list of package or module names from where C extensions may
# be loaded. Extensions are loading into the active Python interpreter and may
# run arbitrary code
extension-pkg-whitelist=numpy

and

[TYPECHECK]

# List of module names for which member attributes should not be checked
# (useful for modules/projects where namespaces are manipulated during runtime
# and thus existing member attributes cannot be deduced by static analysis. It
# supports qualified module names, as well as Unix pattern matching.
ignored-modules=numpy

# List of classes names for which member attributes should not be checked
# (useful for classes with attributes dynamically set). This supports can work
# with qualified names.
ignored-classes=numpy

and it “fixed” my issue.


回答 3

在最新版本的pylint中,您可以添加--extension-pkg-whitelist=numpy到pylint命令中。他们以不安全的方式解决了早期版本中的此问题。现在,如果希望他们更加仔细地查看标准库之外的软件包,则必须将其明确列入白名单。看这里。

In recent versions of pylint you can add --extension-pkg-whitelist=numpy to your pylint command. They had fixed this problem in an earlier version in an unsafe way. Now if you want them to look more carefully at a package outside of the standard library, you must explicitly whitelist it. See here.


回答 4

由于这是google中的最高结果,它给我的印象是您必须忽略所有文件中的警告:

这个问题实际上已经在上个月的pylint / astroid来源https://bitbucket.org/logilab/astroid/commits/83d78af4866be5818f193360c78185e1008fd29e的来源中得到解决, 但尚未在Ubuntu软件包中。

要获取来源,只需

hg clone https://bitbucket.org/logilab/pylint/
hg clone https://bitbucket.org/logilab/astroid
mkdir logilab && touch logilab/__init__.py
hg clone http://hg.logilab.org/logilab/common logilab/common
cd pylint && python setup.py install

因此,最后一步很可能需要一个sudo,当然您也需要一些技巧来克隆。

Since this is the top result in google and it gave me the impression that you have to ignore those warnings in all files:

The problem has actually been fixed in the sources of pylint/astroid last month https://bitbucket.org/logilab/astroid/commits/83d78af4866be5818f193360c78185e1008fd29e but are not yet in the Ubuntu packages.

To get the sources, just

hg clone https://bitbucket.org/logilab/pylint/
hg clone https://bitbucket.org/logilab/astroid
mkdir logilab && touch logilab/__init__.py
hg clone http://hg.logilab.org/logilab/common logilab/common
cd pylint && python setup.py install

whereby the last step will most likely require a sudo and of course you need mercurial to clone.


回答 5

为了忽略numpy.core属性产生的所有错误,我们现在可以使用:

$ pylint a.py --generated-members=numpy.*

作为另一个解决方案,将此选项添加到〜/ .pylintrc/ etc / pylintrc文件中:

[TYPECHECK]

# List of members which are set dynamically and missed by pylint inference
# system, and so shouldn't trigger E1101 when accessed. Python regular
# expressions are accepted.
generated-members=numpy.*

到目前为止,对于有问题的代码来说,这似乎是多余的,但对于另一个模块(即,)仍然很重要。netifaces

For ignoring all the errors generated by numpy.core‘s attributes, we can now use:

$ pylint a.py --generated-members=numpy.*

As another solution, add this option to ~/.pylintrc or /etc/pylintrc file:

[TYPECHECK]

# List of members which are set dynamically and missed by pylint inference
# system, and so shouldn't trigger E1101 when accessed. Python regular
# expressions are accepted.
generated-members=numpy.*

For mentioned in question code by now this seems reduntant, but still matters for another modules, ie. netifaces and etc.


回答 6

如果您不想添加更多配置,请将此代码添加到您的配置文件中,而不是“ whitelist”。

{
"python.linting.pylintArgs": ["--generate-members"],
}

If you don’t want to add more config, please add this code to your config file, instead of ‘whitelist’.

{
"python.linting.pylintArgs": ["--generate-members"],
}

回答 7

在过去的几年中,有许多关于此的错误报告,即https://bitbucket.org/logilab/pylint/issue/58/false-positive-no-member-on-numpy-imports

我建议禁用投诉发生的线路。

# pylint: disable=E1103
print np.zeros([1, 4])
# pylint: enable=E1103

There have been many different bugs reported about this over the past few years i.e. https://bitbucket.org/logilab/pylint/issue/58/false-positive-no-member-on-numpy-imports

I’d suggest disabling for the lines where the complaints occur.

# pylint: disable=E1103
print np.zeros([1, 4])
# pylint: enable=E1103

回答 8

可能是,它与numpy的方法导入的抽象方法混淆了。也就是说,zeros实际上numpy.core.multiarray.zeros是通过numpy语句导入的

from .core import *

依次导入

from .numeric import *

并且以数字形式您会发现

zeros = multiarray.zeros

我想我会代替PyLint感到困惑!

有关PyLint侧面的信息,请参见此错误

Probably, it’s confused with numpy’s abstruse method of methods import. Namely, zeros is in fact numpy.core.multiarray.zeros, imported in numpy with statement

from .core import *

in turn imported with

from .numeric import *

and in numeric you’ll find

zeros = multiarray.zeros

I guess I would be confused in place of PyLint!

See this bug for PyLint side of view.


回答 9

我必须将其添加到我经常使用numpy的任何文件的顶部。

# To ignore numpy errors:
#     pylint: disable=E1101

以防万一有人在日食中遇到Pydev和pylint的麻烦…

I had to add this at the top of any file where I use numpy a lot.

# To ignore numpy errors:
#     pylint: disable=E1101

Just in case someone in eclipse is having trouble with Pydev and pylint…


回答 10

在j_hougs答案的扩展中,您现在可以在.pylintrc的此行中添加有问题的模块,该行在生成时已经准备好为空:

extension-pkg-whitelist=numpy

您可以通过执行以下操作来生成示例.pylintrc:

pylint --generate-rcfile > .pylintrc

然后编辑提到的行

In Extension to j_hougs answer, you can now add the modules in question to this line in .pylintrc, which is already prepared empty on generation:

extension-pkg-whitelist=numpy

you can generate a sample .pylintrc by doing:

pylint --generate-rcfile > .pylintrc

and then edit the mentioned line


回答 11

终于在Pylint 1.8.2中解决了这个问题。开箱即用,无需pylintrc调整!

This has finally been resolved in Pylint 1.8.2. Works out of the box, no pylintrc tweaks needed!


回答 12

这是我针对此问题提出的伪解决方案。

#pylint: disable=no-name-in-module
from numpy import array as np_array, transpose as np_transpose, \
      linspace as np_linspace, zeros as np_zeros
from numpy.random import uniform as random_uniform
#pylint: enable=no-name-in-module

然后,在你的代码,而不是调用numpy功能np.arraynp.zeros等等,你会写np_arraynp_zeros等等。这种做法与在其他的答案提出其他方法的优点:

  • pylint禁用/启用仅限于代码的一小部分
  • 这意味着您不必用pylint指令将每一个调用numpy函数的行都包围起来。
  • 您没有为整个文件执行pylint禁用错误操作,这可能会掩盖代码的其他问题。

明显的缺点是,您必须显式导入您使用的每个numpy函数。该方法可以进一步阐述。您可以定义自己的模块,numpy_importer如下所示

""" module: numpy_importer.py
       explicitely import numpy functions while avoiding pylint errors  
"""
#pylint: disable=unused-import
#pylint: disable=no-name-in-module
from numpy import array, transpose, zeros  #add all things you need  
from numpy.random import uniform as random_uniform
#pylint: enable=no-name-in-module

然后,您的应用程序代码只能将该模块(而不是numpy)导入为

import numpy_importer as np 

并像往常一样使用名称:np.zerosnp.array等等。

这样做的好处是您将拥有一个模块,其中所有numpy相关的导入都将一劳永逸地完成,然后您可以在任意位置使用该行导入它。仍然要注意numpy_importer不要导入不存在的名称,numpy因为这些错误不会被pylint捕获。

This is the pseudo-solution I have come up with for this problem.

#pylint: disable=no-name-in-module
from numpy import array as np_array, transpose as np_transpose, \
      linspace as np_linspace, zeros as np_zeros
from numpy.random import uniform as random_uniform
#pylint: enable=no-name-in-module

Then, in your code, instead of calling numpy functions as np.array and np.zeros and so on, you would write np_array, np_zeros, etc. Advantages of this approach vs. other approaches suggested in other answers:

  • The pylint disable/enable is restricted to a small region of your code
  • That means that you don’t have to surround every single line that has an invocation of a numpy function with a pylint directive.
  • You are not doing pylint disable of the error for your whole file, which might mask other issues with your code.

The clear disadvantage is that you have to explicitely import every numpy function you use. The approach could be elaborated on further. You could define your own module, call it say, numpy_importer as follows

""" module: numpy_importer.py
       explicitely import numpy functions while avoiding pylint errors  
"""
#pylint: disable=unused-import
#pylint: disable=no-name-in-module
from numpy import array, transpose, zeros  #add all things you need  
from numpy.random import uniform as random_uniform
#pylint: enable=no-name-in-module

Then, your application code could import this module only (instead of numpy) as

import numpy_importer as np 

and use the names as usual: np.zeros, np.array etc.

The advantage of this is that you will have a single module in which all numpy related imports are done once and for all, and then you import it with that single line, wherever you want. Still you have to be careful that numpy_importer does not import names that don´t exist in numpy as those errors won’t be caught by pylint.


回答 13

我遇到了numpy,scipy,sklearn,nipy等问题,并通过包裹epylint来解决了这个问题,如下所示:

$猫epylint.py

#!/usr/bin/python

"""
Synopsis: epylint wrapper that filters a bunch of false-positive warnings and errors
Author: DOHMATOB Elvis Dopgima <gmdopp@gmail.com> <elvis.dohmatob@inria.fr>

"""

import os
import sys
import re
from subprocess import Popen, STDOUT, PIPE

NUMPY_HAS_NO_MEMBER = re.compile("Module 'numpy(?:\..+)?' has no '.+' member")
SCIPY_HAS_NO_MEMBER = re.compile("Module 'scipy(?:\..+)?' has no '.+' member")
SCIPY_HAS_NO_MEMBER2 = re.compile("No name '.+' in module 'scipy(?:\..+)?'")
NIPY_HAS_NO_MEMBER = re.compile("Module 'nipy(?:\..+)?' has no '.+' member")
SK_ATTR_DEFINED_OUTSIDE_INIT = re.compile("Attribute '.+_' defined outside __init__")
REL_IMPORT_SHOULD_BE = re.compile("Relative import '.+', should be '.+")
REDEFINING_NAME_FROM_OUTER_SCOPE = re.compile("Redefining name '.+' from outer scope")

if __name__ == "__main__":
    basename = os.path.basename(sys.argv[1])
    for line in Popen(['epylint', sys.argv[1], '--disable=C,R,I'  # filter thesew arnings
                       ], stdout=PIPE, stderr=STDOUT, universal_newlines=True).stdout:
        if line.startswith("***********"):
            continue
        elif line.startswith("No config file found,"):
            continue
        elif "anomalous-backslash-in-string," in line:
            continue
        if NUMPY_HAS_NO_MEMBER.search(line):
            continue
        if SCIPY_HAS_NO_MEMBER.search(line):
            continue
        if SCIPY_HAS_NO_MEMBER2.search(line):
            continue
        if "Used * or ** magic" in line:
            continue
        if "No module named" in line and "_flymake" in line:
            continue
        if SK_ATTR_DEFINED_OUTSIDE_INIT.search(line):
            continue
        if "Access to a protected member" in line:
            continue
        if REL_IMPORT_SHOULD_BE.search(line):
            continue
        if REDEFINING_NAME_FROM_OUTER_SCOPE.search(line):
            continue
        if NIPY_HAS_NO_MEMBER.search(line):
            continue
        # XXX extend by adding more handles for false-positives here
        else:
            print line,

该脚本仅运行epylint,然后刮擦其输出以过滤掉错误肯定的警告和错误。您可以通过添加更多elif案例来扩展它。

注意:如果这适用于您,则您需要修改pychechers.sh,使其像这样

#!/bin/bash

epylint.py "$1" 2>/dev/null
pyflakes "$1"
pep8 --ignore=E221,E701,E202 --repeat "$1"
true

(当然,您必须首先使epylint.py可执行)

这是我的.emacs https://github.com/dohmatob/mydotemacs的链接。希望这对某人有用。

I had this problem with numpy, scipy, sklearn, nipy, etc., and I solved it by wrapping epylint like so:

$ cat epylint.py

#!/usr/bin/python

"""
Synopsis: epylint wrapper that filters a bunch of false-positive warnings and errors
Author: DOHMATOB Elvis Dopgima <gmdopp@gmail.com> <elvis.dohmatob@inria.fr>

"""

import os
import sys
import re
from subprocess import Popen, STDOUT, PIPE

NUMPY_HAS_NO_MEMBER = re.compile("Module 'numpy(?:\..+)?' has no '.+' member")
SCIPY_HAS_NO_MEMBER = re.compile("Module 'scipy(?:\..+)?' has no '.+' member")
SCIPY_HAS_NO_MEMBER2 = re.compile("No name '.+' in module 'scipy(?:\..+)?'")
NIPY_HAS_NO_MEMBER = re.compile("Module 'nipy(?:\..+)?' has no '.+' member")
SK_ATTR_DEFINED_OUTSIDE_INIT = re.compile("Attribute '.+_' defined outside __init__")
REL_IMPORT_SHOULD_BE = re.compile("Relative import '.+', should be '.+")
REDEFINING_NAME_FROM_OUTER_SCOPE = re.compile("Redefining name '.+' from outer scope")

if __name__ == "__main__":
    basename = os.path.basename(sys.argv[1])
    for line in Popen(['epylint', sys.argv[1], '--disable=C,R,I'  # filter thesew arnings
                       ], stdout=PIPE, stderr=STDOUT, universal_newlines=True).stdout:
        if line.startswith("***********"):
            continue
        elif line.startswith("No config file found,"):
            continue
        elif "anomalous-backslash-in-string," in line:
            continue
        if NUMPY_HAS_NO_MEMBER.search(line):
            continue
        if SCIPY_HAS_NO_MEMBER.search(line):
            continue
        if SCIPY_HAS_NO_MEMBER2.search(line):
            continue
        if "Used * or ** magic" in line:
            continue
        if "No module named" in line and "_flymake" in line:
            continue
        if SK_ATTR_DEFINED_OUTSIDE_INIT.search(line):
            continue
        if "Access to a protected member" in line:
            continue
        if REL_IMPORT_SHOULD_BE.search(line):
            continue
        if REDEFINING_NAME_FROM_OUTER_SCOPE.search(line):
            continue
        if NIPY_HAS_NO_MEMBER.search(line):
            continue
        # XXX extend by adding more handles for false-positives here
        else:
            print line,

This script simply runs epylint, then scrapes its output to filter out false-positive warnings and errors. You can extend it by added more elif cases.

N.B.: If this applies to you, then you’ll want to modify your pychechers.sh so it likes like this

#!/bin/bash

epylint.py "$1" 2>/dev/null
pyflakes "$1"
pep8 --ignore=E221,E701,E202 --repeat "$1"
true

(Of course, you have to make epylint.py executable first)

Here is a link to my .emacs https://github.com/dohmatob/mydotemacs. Hope this is useful to someone.


回答 14

这似乎至少在Pylint 1.1.0上有效:

[TYPECHECK]

ignored-classes=numpy

This seems to work on at least Pylint 1.1.0:

[TYPECHECK]

ignored-classes=numpy

回答 15

这个解决方案对我有用

基本上,请从左下角选择齿轮图标=> Setting => Workspace Setting => Extension => Python Configuration =>单击任何Settings.json =>将此添加到文件“ python.linting.pylintArgs”中:[ –extension-pkg-whitelist = numpy“]我正在使用VS 1.27.2

This solution worked for me

Basically, go to Select the gear icon from bottom left=>Setting=>Workspace Setting =>Extension=>Python Configuration=>Click on any Settings.json => add this in the file “python.linting.pylintArgs” : [ “–extension-pkg-whitelist=numpy” ] I am using VS 1.27.2


回答 16

我在另一个不同的模块(kivy.properties)上遇到了同样的问题,它是一个包装好的C模块,例如numpy

使用VSCode V1.38.0,公认的解决方案停止了该项目的所有棉绒。因此,尽管它确实消除了误报no-name-in-module,但并没有真正改善这种情况。

对我来说,最好的解决方法是--ignored-modules在有问题的模块上使用参数。麻烦的是,通过传递任何参数python.linting.pylintArgs抹了默认VSCode设置,所以你需要重新设置者也。那给我留下了以下settings.json文件:

{
    "python.pythonPath": "C:\\Python\\Python37\\python.exe",
    "python.linting.pylintEnabled": true,
    "python.linting.enabled": true,
    "python.linting.pylintArgs": [
        "--ignored-modules=kivy.properties",
        "--disable=all",
        "--enable=F,E,unreachable,duplicate-key,unnecessary-semicolon,global-variable-not-assigned,unused-variable,binary-op-exception,bad-format-string,anomalous-backslash-in-string,bad-open-mode"
    ]
}

I had the same problem with a different module (kivy.properties) which is a wrapped C module like numpy.

Using VSCode V1.38.0, the accepted solution stopped all linting for the project. So, while it did indeed remove the false-positive no-name-in-module, it didn’t really improve the situation.

The best workaround for me was to use the --ignored-modules argument on the offending module. Trouble is, passing any argument via python.linting.pylintArgs wipes out the default VSCode settings, so you need to re-set those also. That left me with the following settings.json file:

{
    "python.pythonPath": "C:\\Python\\Python37\\python.exe",
    "python.linting.pylintEnabled": true,
    "python.linting.enabled": true,
    "python.linting.pylintArgs": [
        "--ignored-modules=kivy.properties",
        "--disable=all",
        "--enable=F,E,unreachable,duplicate-key,unnecessary-semicolon,global-variable-not-assigned,unused-variable,binary-op-exception,bad-format-string,anomalous-backslash-in-string,bad-open-mode"
    ]
}

回答 17

从前面的答案中复制了一些文字,以总结出有效的方法(至少对我来说:debian-jessie)

  1. 在某些旧版本中,pylint存在一个问题,使其无法与numpy(及其他类似软件包)一起使用。

  2. 现在已经解决了该问题,但是出于安全原因,默认情况下禁用了外部C包(C代码的python接口-例如numpy-)。

  3. 您可以创建白名单,以允许pylint在文件中使用它们~/.pylintrc

要运行的基本命令:#仅在您家中没有.pylintrc文件的情况下$ pylint –generate-rcfile> .pylintrc

然后打开文件并添加所需的软件包(extension-pkg-whitelist=用逗号分隔)。使用--extension-pkg-whitelist=numpy命令行中的选项,您可以具有相同的行为。

如果您忽略了本[TYPECHECK]节中的某些软件包,则这pylint将永远不会显示与该软件包相关的错误。实际上,pylint不会告诉您有关那些软件包的任何信息。

A little bit of copy paste from the previous answer to summarize what is working (at least for me: debian-jessie)

  1. In some older version of pylint there was a problem preventing it working with numpy (and other similar packages).

  2. Now that problem has been solved but external C packages (python interfaces to C code -like numpy-) are disabled by default for security reasons.

  3. You can create a white list, to allow pylint to use them in the file ~/.pylintrc.

Basic command to run: # ONLY if you do not already have a .pylintrc file in your home $ pylint –generate-rcfile > .pylintrc

Then open the file and add the packages you want after extension-pkg-whitelist= separated by comma. You can have the same behavior using the option --extension-pkg-whitelist=numpy from the command line.

If you ignore some packages in the [TYPECHECK] section that means that pylint will never show error related to that packages. In practice, pylint will not tell you anything about those packages.


回答 18

我一直在为pylint制作补丁,以解决numpy等库中动态成员的问题。它添加了一个“动态模块”选项,该选项通过实际导入模块来强制检查运行时是否存在成员。请参阅logilab / pylint中的第413期。还有一个拉取请求,请参阅注释之一中的链接。

I’ve been working on a patch to pylint to solve the issue with dynamic members in libraries such as numpy. It adds a “dynamic-modules” option which forces to check if members exist during runtime by making a real import of the module. See Issue #413 in logilab/pylint. There is also a pull request, see link in one of the comments.


回答 19

快速答案:将Pylint更新为1.7.1(如果使用conda管理软件包,请使用conda-forge提供的Pylint 1.7.1)

我在此处的pylint GitHub中发现了类似的问题,有人回复说更新到1.7.1后一切正常。

A quick answer: update Pylint to 1.7.1 (use conda-forge provided Pylint 1.7.1 if you use conda to manage packages)

I found a similar issue in pylint GitHub here and someone replied everything getting OK after updating to 1.7.1.


回答 20

我不确定这是否是解决方案,但是在VSCode中,我在用户设置中明确编写了启用pylint的代码后,所有模块都被识别。

{
    "python.linting.pep8Enabled": true,
    "python.linting.pylintEnabled": true
}

I’m not sure if this is a solution, but in VSCode once I wrote explicitly in my user settings to enable pylint, all modules were recognized.

{
    "python.linting.pep8Enabled": true,
    "python.linting.pylintEnabled": true
}

回答 21

最近(由于spyder或pylint或?有所更改),我从astropy.constants符号的spyder静态代码分析中得到了E1101错误(“无成员”)。不知道为什么。

对于Linux或Unix系统(Mac可能与此类似)上的所有用户,我的简化解决方案是创建一个/ etc / pylintrc,如下所示:

[TYPECHECK]
ignored-modules=astropy.constants

当然,可以将其放在个人$ HOME / .pylintrc文件中。而且,我本可以更新现有文件。

Lately (since something changed in spyder or pylint or ?), I have been getting E1101 errors (“no member”) from spyder’s static code analysis on astropy.constants symbols. No idea why.

My simplistic solution for all users on a Linux or Unix system (Mac is probably similar) is to create an /etc/pylintrc as follows:

[TYPECHECK]
ignored-modules=astropy.constants

Of course, this could, instead, be put in a personal $HOME/.pylintrc file. And, I could have updated an existing file.


PyLint消息:日志记录格式插值

问题:PyLint消息:日志记录格式插值

对于以下代码:

logger.debug('message: {}'.format('test'))

pylint 产生以下警告:

日志记录格式插值(W1202):

在日志记录函数中使用%格式,并将%参数作为参数传递。在日志记录语句的调用形式为“ logging。(format_string.format(format_args …))”时使用。此类调用应改为使用%格式,但通过将参数作为参数传递,将插值留给日志记录函数。

我知道我可以关闭此警告,但我想理解它。我假定使用format()是在Python 3中打印语句的首选方法。为什么这对于logger语句不是正确的?

For the following code:

logger.debug('message: {}'.format('test'))

pylint produces the following warning:

logging-format-interpolation (W1202):

Use % formatting in logging functions and pass the % parameters as arguments Used when a logging statement has a call form of “logging.(format_string.format(format_args…))”. Such calls should use % formatting instead, but leave interpolation to the logging function by passing the parameters as arguments.

I know I can turn off this warning, but I’d like to understand it. I assumed using format() is the preferred way to print out statements in Python 3. Why is this not true for logger statements?


回答 0

logger语句不是正确的,因为它依赖于以前的“%”格式(例如字符串)来使用给logger调用提供的额外参数来对该字符串进行延迟插值。例如,而不是做:

logger.error('oops caused by %s' % exc)

你应该做

logger.error('oops caused by %s', exc)

因此,仅当实际发出消息时才对字符串进行插值。

使用时,您将无法利用此功能.format()


根据文档的“ 优化”部分logging

消息参数的格式将推迟到无法避免为止。但是,计算传递给日志记录方法的参数也可能很昂贵,并且如果记录器将只是丢弃您的事件,则可能要避免这样做。

It is not true for logger statement because it relies on former “%” format like string to provide lazy interpolation of this string using extra arguments given to the logger call. For instance instead of doing:

logger.error('oops caused by %s' % exc)

you should do

logger.error('oops caused by %s', exc)

so the string will only be interpolated if the message is actually emitted.

You can’t benefit of this functionality when using .format().


Per the Optimization section of the logging docs:

Formatting of message arguments is deferred until it cannot be avoided. However, computing the arguments passed to the logging method can also be expensive, and you may want to avoid doing it if the logger will just throw away your event.


回答 1

也许这段时间的差异可以帮助您。

以下描述不是您问题的答案,但可以帮助人们。

对于pylint的2.4:对于中记录样式3个选择.pylintrc文件:oldnewfstr

fstr选项在2.4中添加,在2.5中删除

.pylintrc文件说明(v2.4):

[LOGGING]

# Format style used to check logging format string. `old` means using %
# formatting, `new` is for `{}` formatting,and `fstr` is for f-strings.
logging-format-style=old

对于旧的logging-format-style=old):

foo = "bar"
self.logger.info("foo: %s", foo)

对于logging-format-style=new):

foo = "bar"
self.logger.info("foo: {}", foo)
# OR
self.logger.info("foo: {foo}", foo=foo)

注意:即使选择选项,也无法使用。.format()new

pylint 对于此代码仍然给出相同的警告

self.logger.info("foo: {}".format(foo))  # W1202
# OR
self.logger.info("foo: {foo}".format(foo=foo))  # W1202

对于fstrlogging-format-style=fstr):

foo = "bar"
self.logger.info(f"foo: {foo}")

就个人而言,由于PEP-0498,我更喜欢fstr选项。

Maybe this time differences can help you.

Following description is not the answer for your question, but it can help people.

If you want to use fstrings (Literal String Interpolation) for logging, then you can disable it from .pylintrc file with disable=logging-fstring-interpolation, see: related issue and comment.

Also you can disable logging-format-interpolation.


For pylint 2.4:

There are 3 options for logging style in the .pylintrc file: old, new, fstr

fstr option added in 2.4 and removed in 2.5

Description from .pylintrc file (v2.4):

[LOGGING]

# Format style used to check logging format string. `old` means using %
# formatting, `new` is for `{}` formatting,and `fstr` is for f-strings.
logging-format-style=old

for old (logging-format-style=old):

foo = "bar"
self.logger.info("foo: %s", foo)

for new (logging-format-style=new):

foo = "bar"
self.logger.info("foo: {}", foo)
# OR
self.logger.info("foo: {foo}", foo=foo)

Note: you can not use .format() even if you select new option.

pylint still gives the same warning for this code:

self.logger.info("foo: {}".format(foo))  # W1202
# OR
self.logger.info("foo: {foo}".format(foo=foo))  # W1202

for fstr (logging-format-style=fstr):

foo = "bar"
self.logger.info(f"foo: {foo}")

Personally, I prefer fstr option because of PEP-0498.


回答 2

以我的经验,对于惰性插值而言,比优化(对于大多数用例)更令人信服的原因是,它与Sentry之类的日志聚合器配合得很好。

考虑“用户已登录”日志消息。如果将用户插值到格式字符串中,则与用户一样多的不同日志消息。如果您像这样使用惰性插值,则日志聚合器可以更合理地将其解释为具有多个不同实例的同一条日志消息。

In my experience a more compelling reason than optimization (for most use cases) for the lazy interpolation is that it plays nicely with log aggregators like Sentry.

Consider a ‘user logged in’ log message. If you interpolate the user into the format string, you have as many distinct log messages as there are users. If you use lazy interpolation like this, the log aggregator can more reasonably interpret this as the same log message with a bunch of different instances.


是否可以忽略带有pylint的单个特定行?

问题:是否可以忽略带有pylint的单个特定行?

标头中包含以下行:

import config.logging_settings

这实际上改变了我的python日志记录设置,但是pylint认为这是未使用的导入。我一般不希望删除unused-import警告,因此可以忽略这一行吗?

我不介意.pylintrc为此项目准备一个,因此更改配置文件的答案将被接受。

否则,这样的事情也将不胜感激:

import config.logging_settings # pylint: disable-this-line-in-some-way

I have the following line in my header:

import config.logging_settings

This actually changes my python logging settings, but pylint thinks it is an unused import. I do not want to remove unused-import warnings in general so is it possible to just ignore this one specific line?

I wouldn’t mind having a .pylintrc for this project so answers changing a config file will be accepted.

Otherwise, something like this will also be appreciated:

import config.logging_settings # pylint: disable-this-line-in-some-way

回答 0

Pylint信息控件记录在Pylint手册中

是否可以在本地禁用特定消息?

是的,此功能已在Pylint 0.11中添加。这可以通过
# pylint: disable=some-message,another-one
在所需的块级别或所需的代码行的末尾添加来完成

您可以使用消息代码或符号名。

例如

def test():
    # Disable all the no-member violations in this function
    # pylint: disable=no-member
    ...
global VAR # pylint: disable=global-statement

该手册还有更多示例

一个Wiki,记录所有pylint消息及其代码。

Pylint message control is documented in the Pylint manual:

Is it possible to locally disable a particular message?

Yes, this feature has been added in Pylint 0.11. This may be done by adding
# pylint: disable=some-message,another-one
at the desired block level or at the end of the desired line of code

You can use the message code or the symbolic names.

For example

def test():
    # Disable all the no-member violations in this function
    # pylint: disable=no-member
    ...
global VAR # pylint: disable=global-statement

The manual also has further examples.

There is a wiki that documents all pylint messages and their codes.


回答 1

import config.logging_settings # pylint: disable=W0611

这很简单,并且专门针对该行。

正如sthenault所指出的那样,您可以并且应该使用更具可读性的形式:

import config.logging_settings # pylint: disable=unused-import
import config.logging_settings # pylint: disable=W0611

That was simple and is specific for that line.

As sthenault kindly pointed out, you can and should use the more readable form:

import config.logging_settings # pylint: disable=unused-import

回答 2

我相信您正在寻找的是…

import config.logging_settings  # @UnusedImport

注意注释前的双倍空格,以免出现其他格式警告。

另外,根据您的IDE(如果使用的是IDE),可能有一个选项可以添加正确的忽略规则(例如,Ctrl1在光标悬停时按eclipse键,警告将自动建议@UnusedImport

I believe what you’re looking for is…

import config.logging_settings  # @UnusedImport

Note the double space before the comment to avoid hitting other formatting warnings.

Also, depending on your IDE (if you’re using one), there’s probably an option to add the correct ignore rule (eg in eclipse pressing Ctrl1 while the cursor is over the warning will auto-suggest @UnusedImport


回答 3

https://github.com/PyCQA/pylint/tree/master/pylint/checkers中检出文件。我没有找到比Ctrl + F-ing这些文件或使用Github搜索功能更好的从消息中获取错误名称的方法:

如果消息是“模块…中没有名称…”,请使用搜索:

No name %r in module %r repo:PyCQA/pylint/tree/master path:/pylint/checkers

或者,为了获得更少的结果:

"No name %r in module %r" repo:PyCQA/pylint/tree/master path:/pylint/checkers

Github将向您展示:

"E0611": (
    "No name %r in module %r",
    "no-name-in-module",
    "Used when a name cannot be found in a module.",

然后,您可以执行以下操作:

from collections import Sequence # pylint: disable=no-name-in-module

Checkout the files in https://github.com/PyCQA/pylint/tree/master/pylint/checkers. I haven’t found a better way to obtain the error name from a message than either Ctrl+F-ing those files or using the Github search feature:

If the message is “No name … in module …”, use the search:

No name %r in module %r repo:PyCQA/pylint/tree/master path:/pylint/checkers

Or, to get less results:

"No name %r in module %r" repo:PyCQA/pylint/tree/master path:/pylint/checkers

Github will show you:

"E0611": (
    "No name %r in module %r",
    "no-name-in-module",
    "Used when a name cannot be found in a module.",

You can then do:

from collections import Sequence # pylint: disable=no-name-in-module

在Django中使用Pylint

问题:在Django中使用Pylint

我非常想将pylint集成到我的python项目的构建过程中,但是我遇到了一个问题:我发现一种非常有用的错误类型:– E1101: *%s %r has no %r member*在使用通用django字段时不断报告错误, 例如:

E1101:125:get_user_tags: Class 'Tag' has no 'objects' member

这是由以下代码引起的:

def get_user_tags(username):
   """
   Gets all the tags that username has used.

   Returns a query set.
   """
   return Tag.objects.filter(  ## This line triggers the error.
       tagownership__users__username__exact=username).distinct()

# Here is the Tag class, models.Model is provided by Django:
class Tag(models.Model):
   """
   Model for user-defined strings that help categorize Events on
   on a per-user basis.
   """
   name = models.CharField(max_length=500, null=False, unique=True)

   def __unicode__(self):
       return self.name

如何调整Pylint以适当考虑诸如对象之类的字段?(我也研究了Django的源代码,但无法找到的实现objects,因此我怀疑它不是“只是”一个类字段。另一方面,我对python还是很陌生,所以我可能已经忽略了一些东西。)

编辑:我发现告诉pylint不要警告这些警告的唯一方法是阻止所有类型为(E1101)的错误,这是不可接受的解决方案,因为(在我看来)这是一个非常有用的错误。如果还有另一种方法,而又不增加pylint的来源,请给我指出细节:)

这里对于我已经受够了问题的总结pycheckerpyflakes-他们已经被证明是远远不稳定的一般用途。(在pychecker的情况下,崩溃源于pychecker代码-并非源于正在加载/调用的源。)

I would very much like to integrate pylint into the build process for my python projects, but I have run into one show-stopper: One of the error types that I find extremely useful–:E1101: *%s %r has no %r member*–constantly reports errors when using common django fields, for example:

E1101:125:get_user_tags: Class 'Tag' has no 'objects' member

which is caused by this code:

def get_user_tags(username):
   """
   Gets all the tags that username has used.

   Returns a query set.
   """
   return Tag.objects.filter(  ## This line triggers the error.
       tagownership__users__username__exact=username).distinct()

# Here is the Tag class, models.Model is provided by Django:
class Tag(models.Model):
   """
   Model for user-defined strings that help categorize Events on
   on a per-user basis.
   """
   name = models.CharField(max_length=500, null=False, unique=True)

   def __unicode__(self):
       return self.name

How can I tune Pylint to properly take fields such as objects into account? (I’ve also looked into the Django source, and I have been unable to find the implementation of objects, so I suspect it is not “just” a class field. On the other hand, I’m fairly new to python, so I may very well have overlooked something.)

Edit: The only way I’ve found to tell pylint to not warn about these warnings is by blocking all errors of the type (E1101) which is not an acceptable solution, since that is (in my opinion) an extremely useful error. If there is another way, without augmenting the pylint source, please point me to specifics :)

See here for a summary of the problems I’ve had with pychecker and pyflakes — they’ve proven to be far to unstable for general use. (In pychecker’s case, the crashes originated in the pychecker code — not source it was loading/invoking.)


回答 0

不要通过添加ignores或禁用或削弱Pylint功能generated-members
使用积极开发的理解 Django的Pylint插件。
这个适用于Django的Pylint插件效果很好:

pip install pylint-django

并且在运行pylint时,将以下标志添加到命令中:

--load-plugins pylint_django

详细的博客文章在这里

Do not disable or weaken Pylint functionality by adding ignores or generated-members.
Use an actively developed Pylint plugin that understands Django.
This Pylint plugin for Django works quite well:

pip install pylint-django

and when running pylint add the following flag to the command:

--load-plugins pylint_django

Detailed blog post here.


回答 1

我使用以下内容: pylint --generated-members=objects

I use the following: pylint --generated-members=objects


回答 2

我的〜/ .pylintrc包含

[TYPECHECK]
generated-members=REQUEST,acl_users,aq_parent,objects,_meta,id

最后两个是专门针对Django的。

请注意,PyLint 0.21.1中存在一个错误,需要对其进行修补才能使其正常工作。

编辑:弄乱了一点之后,我决定对PyLint进行一点修改,以允许我将以上内容扩展为:

[TYPECHECK]
generated-members=REQUEST,acl_users,aq_parent,objects,_meta,id,[a-zA-Z]+_set

我只是添加:

    import re
    for pattern in self.config.generated_members:
        if re.match(pattern, node.attrname):
            return

在错误报告中提到的修复之后(即,在第129行)。

快乐的时光!

My ~/.pylintrc contains

[TYPECHECK]
generated-members=REQUEST,acl_users,aq_parent,objects,_meta,id

the last two are specifically for Django.

Note that there is a bug in PyLint 0.21.1 which needs patching to make this work.

Edit: After messing around with this a little more, I decided to hack PyLint just a tiny bit to allow me to expand the above into:

[TYPECHECK]
generated-members=REQUEST,acl_users,aq_parent,objects,_meta,id,[a-zA-Z]+_set

I simply added:

    import re
    for pattern in self.config.generated_members:
        if re.match(pattern, node.attrname):
            return

after the fix mentioned in the bug report (i.e., at line 129).

Happy days!


回答 3

如果您使用Visual Studio Code,请执行以下操作:

pip install pylint-django

并添加到VSC配置:

"python.linting.pylintArgs": [
    "--load-plugins=pylint_django"
],

If you use Visual Studio Code do this:

pip install pylint-django

And add to VSC config:

"python.linting.pylintArgs": [
    "--load-plugins=pylint_django"
],

回答 4

django-lint是一个不错的工具,它使用django特定的设置包装pylint:http ://chris-lamb.co.uk/projects/django-lint/

github项目:https : //github.com/lamby/django-lint

django-lint is a nice tool which wraps pylint with django specific settings : http://chris-lamb.co.uk/projects/django-lint/

github project: https://github.com/lamby/django-lint


回答 5

由于pylint的工作方式(它在不让Python实际执行的情况下检查源代码本身)对pylint来说很难弄清楚元类和复杂的基类实际上如何影响类及其实例。在这方面,“ pychecker”工具要好一些,因为它确实允许Python执行代码。它导入模块并检查生成的对象。但是,该方法还有其他问题,因为它确实允许Python执行代码:-)

您可以扩展pylint来教它有关Django所使用的魔术的知识,或者使它更好地理解元类或复杂的基类,或者在检测到一个或多个它不太了解的功能之后忽略这些情况。我认为这不会特别容易。您还可以通过源代码中的特殊注释,命令行选项或.pylintrc文件,告诉pylint不要警告这些事情。

Because of how pylint works (it examines the source itself, without letting Python actually execute it) it’s very hard for pylint to figure out how metaclasses and complex baseclasses actually affect a class and its instances. The ‘pychecker’ tool is a bit better in this regard, because it does actually let Python execute the code; it imports the modules and examines the resulting objects. However, that approach has other problems, because it does actually let Python execute the code :-)

You could extend pylint to teach it about the magic Django uses, or to make it understand metaclasses or complex baseclasses better, or to just ignore such cases after detecting one or more features it doesn’t quite understand. I don’t think it would be particularly easy. You can also just tell pylint to not warn about these things, through special comments in the source, command-line options or a .pylintrc file.


回答 6

我从使用pylint / pychecker辞职,转而将pyflakes与Django代码一起使用-它只是尝试导入模块并报告发现的任何问题,例如未使用的导入或未初始化的本地名称。

I resigned from using pylint/pychecker in favor of using pyflakes with Django code – it just tries to import module and reports any problem it finds, like unused imports or uninitialized local names.


回答 7

这不是解决方案,但是您可以在objects = models.Manager()不更改任何行为的情况下将其添加到Django模型中。

我本人只使用pyflakes,主要是因为我的部分pylint和惰性有些愚蠢的默认设置(不想查看如何更改默认设置)。

This is not a solution, but you can add objects = models.Manager() to your Django models without changing any behavior.

I myself only use pyflakes, primarily due to some dumb defaults in pylint and laziness on my part (not wanting to look up how to change the defaults).


回答 8

尝试与运行pylint

pylint --ignored-classes=Tags

如果可行,添加所有其他Django类-可能使用脚本,例如python:P

该文档--ignore-classes是:

--ignored-classes=<members names>
不应检查其成员属性的类名列表(对于动态设置了属性的类很有用)。[当前:%default]

我认为这并不是一个特别优雅的解决方案,但应该可以。

Try running pylint with

pylint --ignored-classes=Tags

If that works, add all the other Django classes – possibly using a script, in say, python :P

The documentation for --ignore-classes is:

--ignored-classes=<members names>
List of classes names for which member attributes should not be checked (useful for classes with attributes dynamicaly set). [current: %default]

I should add this is not a particular elegant solution in my view, but it should work.


回答 9

另一个问题中提出的解决方案是,只需将get_attr添加到Tag类中即可。丑陋,但是行得通。

The solution proposed in this other question it to simply add get_attr to your Tag class. Ugly, but works.


回答 10

到目前为止,我没有找到真正的解决方案,但是可以解决:

  • 在我们公司,我们要求pylint得分>8。这允许pylint无法理解编码实践,同时确保代码不太“异常”。到目前为止,我们还没有看到E1101阻止我们达到8分或更高分数的情况。
  • 我们的“ make check”目标过滤掉“ for has no’objects member”消息,以消除由于pylint不了解Django引起的大部分干扰。

So far I have found no real solution to that but work around:

  • In our company we require a pylint score > 8. This allows coding practices pylint doesn’t understand while ensuring that the code isn’t too “unusual”. So far we havn’t seen any instance where E1101 kept us from reaching a score of 8 or higher.
  • Our ‘make check’ targets filter out “for has no ‘objects’ member” messages to remove most of the distraction caused by pylint not understanding Django.

回答 11

对于neovim & vim8使用w0rp's ale插件。如果您已经安装了正确的一切,包括w0rp's alepylintpylint-django。在您的代码中vimrc添加以下内容,并享受使用django开发Web应用程序的乐趣。谢谢。

let g:ale_python_pylint_options = '--load-plugins pylint_django'

For neovim & vim8 use w0rp's ale plugin. If you have installed everything correctly including w0rp's ale, pylint & pylint-django. In your vimrc add the following line & have fun developing web apps using django. Thanks.

let g:ale_python_pylint_options = '--load-plugins pylint_django'

为什么Pylint认为在条件值中使用len(SEQUENCE)不正确?

问题:为什么Pylint认为在条件值中使用len(SEQUENCE)不正确?

考虑以下代码片段:

from os import walk

files = []
for (dirpath, _, filenames) in walk(mydir):
    # more code that modifies files
if len(files) == 0: # <-- C1801
    return None

Pylint使我对有关if语句行的消息感到震惊:

[pylint] C1801:请勿len(SEQUENCE)用作条件值

乍一看,规则C1801在我看来并不十分合理,参考指南中的定义也无法解释为什么这是一个问题。实际上,它彻头彻尾地称其为不正确的用法

len-as-condition(C1801)不要len(SEQUENCE)用作条件值当Pylint检测到内部条件不正确使用len(sequence)时使用。

我的搜索尝试也未能为我提供更深入的解释。我确实知道,序列的length属性可能会被延迟评估,并且__len__可以编程为具有副作用,但是令人怀疑的是,仅此一个问题是否足以使Pylint认为这种用法不正确。因此,在我简单地将项目配置为忽略规则之前,我想知道我的推理中是否缺少某些内容。

什么时候将len(SEQ)用作条件值有问题?Pylint尝试使用C1801避免哪些主要情况?

Considering this code snippet:

from os import walk

files = []
for (dirpath, _, filenames) in walk(mydir):
    # more code that modifies files
if len(files) == 0: # <-- C1801
    return None

I was alarmed by Pylint with this message regarding the line with the if statement:

[pylint] C1801:Do not use len(SEQUENCE) as condition value

The rule C1801, at first glance, did not sound very reasonable to me, and the definition on the reference guide does not explain why this is a problem. In fact, it downright calls it an incorrect use.

len-as-condition (C1801): Do not use len(SEQUENCE) as condition value Used when Pylint detects incorrect use of len(sequence) inside conditions.

My search attempts have also failed to provide me a deeper explanation. I do understand that a sequence’s length property may be lazily evaluated, and that __len__ can be programmed to have side effects, but it is questionable whether that alone is problematic enough for Pylint to call such a use incorrect. Hence, before I simply configure my project to ignore the rule, I would like to know whether I am missing something in my reasoning.

When is the use of len(SEQ) as a condition value problematic? What major situations is Pylint attempting to avoid with C1801?


回答 0

什么时候将len(SEQ)用作条件值有问题?Pylint尝试使用C1801避免哪些主要情况?

使用它并不是真的有问题len(SEQUENCE)-尽管它可能没有效率那么高(请参阅chepner的评论)。无论如何,Pylint会检查代码是否符合PEP 8样式指南,该指南指出

对于序列(字符串,列表,元组),请使用空序列为假的事实。

Yes: if not seq:
     if seq:

No:  if len(seq):
     if not len(seq):

作为偶尔在各种语言之间徘徊的Python程序员,我认为该len(SEQUENCE)结构更具可读性和显式性(“显式优于隐式”)。但是,使用空序列False在布尔上下文中求值的事实被认为更“ Pythonic”。

When is the use of len(SEQ) as a condition value problematic? What major situations is Pylint attempting to avoid with C1801?

It’s not really problematic to use len(SEQUENCE) – though it may not be as efficient (see chepner’s comment). Regardless, Pylint checks code for compliance with the PEP 8 style guide which states that

For sequences, (strings, lists, tuples), use the fact that empty sequences are false.

Yes: if not seq:
     if seq:

No:  if len(seq):
     if not len(seq):

As an occasional Python programmer, who flits between languages, I’d consider the len(SEQUENCE) construct to be more readable and explicit (“Explicit is better then implicit”). However, using the fact that an empty sequence evaluates to False in a Boolean context is considered more “Pythonic”.


回答 1

请注意,使用NumPy数组时,实际上需要使用len(seq)(而不是仅检查seq的bool值)。

a = numpy.array(range(10))
if a:
    print "a is not empty"

导致异常:ValueError:具有多个元素的数组的真值不明确。使用a.any()或a.all()

因此,对于同时使用Python列表和NumPy数组的代码,C1801消息的用处不大。

Note that the use of len(seq) is in fact required (instead of just checking the bool value of seq) when using NumPy arrays.

a = numpy.array(range(10))
if a:
    print "a is not empty"

results in an exception: ValueError: The truth value of an array with more than one element is ambiguous. Use a.any() or a.all()

And hence for code that uses both Python lists and NumPy arrays, the C1801 message is less than helpful.


回答 2

这是pylint中的问题,并且不再视为len(x) == 0不正确。

您不应以裸露 len(x)为条件。比较len(x)反对一个明确的值,如if len(x) == 0if len(x) > 0是PEP 8完全正常和不禁止。

PEP 8

# Correct:
if not seq:
if seq:

# Wrong:
if len(seq):
if not len(seq):

请注意,不禁止明确测试长度Python禅宗指出:

显式胜于隐式。

在这两者之间的选择if not seqif not len(seq),无一不是隐含的,而行为是不同的。但是if len(seq) == 0或者if len(seq) > 0是显式比较,并且在许多情况下是正确的行为。

在pylint中,PR 2815修复了此错误,该错误首先报告为问题2684。它会继续抱怨if len(seq),但不再抱怨if len(seq) > 0。PR已在2019-03-19合并,因此如果您使用的是pylint 2.4(于2019-09-14发布),则不应看到此问题。

This was a issue in pylint, and it no longer considers len(x) == 0 as incorrect.

You should not use a bare len(x) as a condition. Comparing len(x) against an explicit value, such as if len(x) == 0 of if len(x) > 0 is totally fine and not prohibited by PEP 8.

From PEP 8:

# Correct:
if not seq:
if seq:

# Wrong:
if len(seq):
if not len(seq):

Note that explicitly testing for the length is not prohibited. The Zen of Python states:

Explicit is better than implicit.

In the choice between if not seq and if not len(seq), both are implicit but behaviour is different. But if len(seq) == 0 or if len(seq) > 0 are explicit comparisons and in many contexts the correct behaviour.

In pylint, PR 2815 has fixed this bug, first reported as issue 2684. It will continue to complain about if len(seq), but it will no longer complain about if len(seq) > 0. The PR was merged 2019-03-19 so if you are using pylint 2.4 (released 2019-09-14) you should not see this problem.


回答 3

Pylint未能提供我的代码,研究使我转向了这篇文章:

../filename.py:49:11: C1801: Do not use `len(SEQUENCE)` to determine if a sequence is empty (len-as-condition)
../filename.py:49:34: C1801: Do not use `len(SEQUENCE)` to determine if a sequence is empty (len-as-condition)

这是我之前的代码:

def list_empty_folders(directory):
"""The Module Has Been Build to list empty Mac Folders."""
for (fullpath, dirnames, filenames) in os.walk(directory):
    if len(dirnames) == 0 and len(filenames) == 0:
        print("Exists: {} : Absolute Path: {}".format(
            os.path.exists(fullpath), os.path.abspath(fullpath)))

这是我的代码修复之后。通过使用int() attribute,我似乎对Pep8 / Pylint感到满意,并且似乎对我的代码没有负面影响:

def list_empty_folders(directory):
"""The Module Has Been Build to list empty Mac Folders."""
for (fullpath, dirnames, filenames) in os.walk(directory):
    if len(dirnames).__trunc__() == 0 and len(filenames).__trunc__() == 0:
        print("Exists: {} : Absolute Path: {}".format(
            os.path.exists(fullpath), os.path.abspath(fullpath)))

我的修复

通过增加.__trunc__()顺序,似乎已经解决了需求。

我的行为没有区别,但是如果有人知道我所缺少的细节,请告诉我。

Pylint was failing for my code and research led me to this post:

../filename.py:49:11: C1801: Do not use `len(SEQUENCE)` to determine if a sequence is empty (len-as-condition)
../filename.py:49:34: C1801: Do not use `len(SEQUENCE)` to determine if a sequence is empty (len-as-condition)

This was my code before:

def list_empty_folders(directory):
"""The Module Has Been Build to list empty Mac Folders."""
for (fullpath, dirnames, filenames) in os.walk(directory):
    if len(dirnames) == 0 and len(filenames) == 0:
        print("Exists: {} : Absolute Path: {}".format(
            os.path.exists(fullpath), os.path.abspath(fullpath)))

This was after my code fix. By using the int() attribute, I seem to have satisfied the Pep8/Pylint and doesn’t seem to have a negative impact on my code:

def list_empty_folders(directory):
"""The Module Has Been Build to list empty Mac Folders."""
for (fullpath, dirnames, filenames) in os.walk(directory):
    if len(dirnames).__trunc__() == 0 and len(filenames).__trunc__() == 0:
        print("Exists: {} : Absolute Path: {}".format(
            os.path.exists(fullpath), os.path.abspath(fullpath)))

My Fix

By adding .__trunc__() to the sequence it seems to have settled the need.

I do not see a difference in the behaviour, but if anyone knows specifics that I am missing, please let me know.


如何禁用Pylint警告?

问题:如何禁用Pylint警告?

我正在尝试在Pylint 0.21.1中禁用警告C0321(“在一行上有多个语句” –我经常将if具有短单行结果的语句放在同一行上)(如果重要:astng 0.20)。 1,常见的0.50.3,Python 2.6.6(r266:84292,2010年9月15日,16:22:56)。

我尝试添加disable=C0321Pylint配置文件,但是Pylint坚持要报告它。该行的变化(例如disable=0321disable=C321)被标记为错误,因此Pylint 确实正确识别了该选项,只是忽略了它。

这是Pylint的错误,还是我做错了什么?有没有办法解决?我真的很想摆脱一些杂音。

I’m trying to disable warning C0321 (“more than one statement on a single line” — I often put if statements with short single-line results on the same line), in Pylint 0.21.1 (if it matters: astng 0.20.1, common 0.50.3, Python 2.6.6 (r266:84292, Sep 15 2010, 16:22:56)).

I’ve tried adding disable=C0321 in the Pylint configuration file, but Pylint insists on reporting it anyway. Variations on that line (like disable=0321 or disable=C321) are flagged as errors, so Pylint does recognize the option properly, it’s just ignoring it.

Is this a Pylint bug, or am I doing something wrong? Is there any way around this? I’d really like to get rid of some of this noise.


回答 0

pylint --generate-rcfile 显示如下:

[MESSAGES CONTROL]

# Enable the message, report, category or checker with the given id(s). You can
# either give multiple identifier separated by comma (,) or put this option
# multiple time.
#enable=

# Disable the message, report, category or checker with the given id(s). You
# can either give multiple identifier separated by comma (,) or put this option
# multiple time (only on the command line, not in the configuration file where
# it should appear only once).
#disable=

因此,看起来您~/.pylintrc应该disable=在section中有一行[MESSAGES CONTROL]

pylint --generate-rcfile shows it like this:

[MESSAGES CONTROL]

# Enable the message, report, category or checker with the given id(s). You can
# either give multiple identifier separated by comma (,) or put this option
# multiple time.
#enable=

# Disable the message, report, category or checker with the given id(s). You
# can either give multiple identifier separated by comma (,) or put this option
# multiple time (only on the command line, not in the configuration file where
# it should appear only once).
#disable=

So it looks like your ~/.pylintrc should have the disable= line/s in it inside a section [MESSAGES CONTROL].


回答 1

我在使用Eclipse时遇到了此问题,并按以下步骤解决了该问题:

在pylint文件夹(例如C:\Python26\Lib\site-packages\pylint)中,按住shift键并单击鼠标右键,然后选择打开该文件夹中的Windows命令。类型:

lint.py --generate-rcfile > standard.rc

这将创建standard.rc配置文件。在记事本中打开它[MESSAGES CONTROL],取消注释, disable=然后添加要禁用的消息ID,例如:

disable=W0511, C0321

保存文件,然后在Eclipse-> window-> preferences-> PyDev-> pylint的参数框中,键入:

--rcfile=C:\Python26\Lib\site-packages\pylint\standard.rc

现在应该可以了…


您还可以在代码的顶部添加注释,该注释将由pylint解释:

# pylint: disable=C0321

链接到所有pylint消息代码


--disable-ids=C0321在参数框中添加例如无效。所有可用的pylint消息都存储在字典中_messages,字典是pylint.utils.MessagesHandlerMixIn该类实例的属性。当使用带有参数--disable-ids=...(至少没有配置文件)运行pylint时,此字典最初为空,从而在pylint(pylint.utils.MessagesHandlerMixIn.check_message_id()。中引发KeyError异常。在Eclipse中,您可以在Pylint 控制台中看到此错误消息(windows-show view-Console ,从控制台图标旁边的控制台选项中选择Pylint控制台。)

I had this problem using Eclipse and solved it as follows:

in the pylint folder (e.g. C:\Python26\Lib\site-packages\pylint), hold shift, right-click and choose to open the windows command in that folder. Type:

lint.py --generate-rcfile > standard.rc

This creates the standard.rc configuration file. Open it in notepad and under [MESSAGES CONTROL], uncomment disable= and add the message ID’s you want to disable, e.g.:

disable=W0511, C0321

Save the file, and in Eclipse->window->preferences->PyDev->pylint, in the arguments box, type:

--rcfile=C:\Python26\Lib\site-packages\pylint\standard.rc

Now it should work …


You can also add a comment at the top of your code that will be interpreted by pylint:

# pylint: disable=C0321

link to all pylint message codes


Adding e.g. --disable-ids=C0321 in the arguments box does not work. All available pylint messages are stored in the dictionary _messages, an attribute of an instance of the pylint.utils.MessagesHandlerMixIn class. When running pylint with the argument --disable-ids=... (at least without a config file), this dictionary is initially empty, raising a KeyError exception within pylint (pylint.utils.MessagesHandlerMixIn.check_message_id(). In Eclipse, you can see this error-message in the Pylint Console (windows – show view – Console, select Pylint console from the console options besides the console icon.)


回答 2

从Pylint v。0.25.3开始,您可以使用符号名来禁用警告,而不必记住所有这些代码号。例如:

# pylint: disable=locally-disabled, multiple-statements, fixme, line-too-long

这种样式比隐式错误代码更具启发性,并且也更实用,因为较新版本的Pylint仅输出符号名称,而不输出错误代码。

符号名和代码之间的对应关系可以在此处找到。

可以在其自己的行上插入禁用注释,将禁用应用于同一块之后的所有内容。或者,可以将其插入要应用的行的末尾。

如果pylint输出“ Locally disabling”消息,您可以通过在上面的示例中locally-disabled 首先包含disable来摆脱它们。

Starting from Pylint v. 0.25.3, you can use the symbolic names for disabling warnings instead of having to remember all those code numbers. E.g.:

# pylint: disable=locally-disabled, multiple-statements, fixme, line-too-long

This style is more instructive than cryptic error codes, and also more practical since newer versions of Pylint only output the symbolic name, not the error code.

The correspondence between symbolic names and codes can be found here.

A disable comment can be inserted on its own line, applying the disable to everything that comes after in the same block. Alternatively, it can be inserted at the end of the line for which it is meant to apply.

If pylint outputs “Locally disabling” messages, you can get rid of them by including the disable locally-disabled first as in the example above.


回答 3

要在块中本地禁用警告,请添加

# pylint: disable=C0321

到那个街区。

To disable a warning locally in a block, add

# pylint: disable=C0321

to that block.


回答 4

有几种方法可以从Pylint禁用警告和错误。使用哪一个与您要在全局或本地应用禁用功能的方式有关—这是一项重要的设计决策。

多种方法

  1. 在一个或多个pylintrc文件中。

这涉及的不只是~/.pylintrcChris Morgan描述的文件(在$ HOME目录中)。Pylint将搜索rc文件,其优先级是对“ closer”文件的重视程度更高:

  • 一个pylintrc在当前工作目录下的文件; 要么

  • 如果当前工作目录在Python模块中(即它包含一个__init__.py文件),则搜索Python模块的层次结构,直到pylintrc找到一个文件;要么

  • 该文件由环境变量PYLINTRC命名;要么

  • 如果您的主目录不是/root

    • ~/.pylintrc; 要么

    • ~/.config/pylintrc; 要么

    • /etc/pylintrc

请注意,其中大多数文件都已命名pylintrc-仅其中的文件~带有前导点。

在您的pylintrc文件中,添加行以禁用特定的pylint消息。例如:

[MESSAGES CONTROL]
disable=locally-disabled
  1. pylint如Aboo和Cairnarvon所述,从命令行进一步禁用。看起来像pylint --disable=bad-builtin。重复--disable以取消显示其他项目。

  2. 如Imolit所述,从各个Python代码行进一步禁用。它们看起来像some statement # pylint: disable=broad-except(在原始源代码行的末尾加了注释),仅适用于当前行。我的方法是始终将它们放在其他代码行的末尾,以免它们与块样式混淆,请参见下文。

  3. 为更大的Python代码块定义的进一步禁用功能,直至完整的源文件。

    • 这些看起来像# pragma pylint: disable=bad-whitespace(请注意pragma关键字)。

    • 这些适用于编译指示每一行。在文件的顶部放置一个这样的块可以使抑制作用适用于整个文件。将同一块放在文件的较低位置,使它们仅适用于该块之后的行。我的方法是始终将它们放在自己的一行上,这样它们就不会与单行样式混淆,请参见上文。

    • 当抑制仅在代码范围内适用时,请使用# pragma pylint: enable=bad-whitespace(现在使用enablenot disable)停止抑制。

请注意,禁用单行将使用# pylint语法,而禁用此行以后将使用# pragma pylint语法。这些很容易混淆,尤其是在复制和粘贴时。

放在一起

我通常混合使用这些方法。

  • 我使用~/.pylintrc绝对的全球标准-其中很少。

  • pylintrc当存在特定于项目的标准时,我在Python模块中的不同级别使用项目级。特别是当您从另一个人或团队那里获取代码时,您可能会发现他们使用了您不希望使用的约定,但是您不想重做代码。将设置保持在此级别不会有助于将这些做法传播到其他项目。

  • 我在单个源文件的顶部使用块样式实用程序。即使对于我不同意的Pylint标准,我也喜欢在开发热时关闭编译指示(停止抑制消息)(例如“公共方法太少-我总是在自定义Exception类上得到警告”),但是在开发过程中查看更多(也许所有Pylint消息)很有帮助。这样,您可以找到要使用单行编译指示解决的情况(请参见下文),或仅为下一个开发人员添加注释,以解释为什么在这种情况下可以接受该警告。

  • 即使在代码准备好检入的情况下,我仍然启用了一些块样式的编译指示。我尝试使用其中的一些,但是当对模块有意义时,可以作为文档来使用。但是,我尝试保留尽可能少的内容,最好不保留任何内容。

  • 我使用单行注释样式来解决特别是潜在的错误。例如,如果有实际可行的地方,那么except Exception as exc我将其# pylint: disable=broad-except放在这行上,而不是采用更全局的方法,因为这是一个奇怪的exceptions,需要以基本上是一种文档形式的形式予以提及。


像Python中的所有其他内容一样,您可以在不同级别的间接操作。我的建议是考虑什么属于哪个级别,这样您就不会对Pylint过于宽容。

There are several ways to disable warnings & errors from Pylint. Which one to use has to do with how globally or locally you want to apply the disablement — an important design decision.

Multiple Approaches

  1. In one or more pylintrc files.

This involves more than the ~/.pylintrc file (in your $HOME directory) as described by Chris Morgan. Pylint will search for rc files, with a precedence that values “closer” files more highly:

  • A pylintrc file in the current working directory; or

  • If the current working directory is in a Python module (i.e. it contains an __init__.py file), searching up the hierarchy of Python modules until a pylintrc file is found; or

  • The file named by the environment variable PYLINTRC; or

  • If you have a home directory that isn’t /root:

    • ~/.pylintrc; or

    • ~/.config/pylintrc; or

    • /etc/pylintrc

Note that most of these files are named pylintrc — only the file in ~ has a leading dot.

To your pylintrc file, add lines to disable specific pylint messages. For example:

[MESSAGES CONTROL]
disable=locally-disabled
  1. Further disables from the pylint command line, as described by Aboo and Cairnarvon. This looks like pylint --disable=bad-builtin. Repeat --disable to suppress additional items.

  2. Further disables from individual Python code lines, as described by Imolit. These look like some statement # pylint: disable=broad-except (extra comment on the end of the original source line) and apply only to the current line. My approach is to always put these on the end of other lines of code so they won’t be confused with the block style, see below.

  3. Further disables defined for larger blocks of Python code, up to complete source files.

    • These look like # pragma pylint: disable=bad-whitespace (note the pragma key word).

    • These apply to every line after the pragma. Putting a block of these at the top of a file makes the suppressions apply to the whole file. Putting the same block lower in the file makes them apply only to lines following the block. My approach is to always put these on a line of their own so they won’t be confused with the single-line style, see above.

    • When a suppression should only apply within a span of code, use # pragma pylint: enable=bad-whitespace (now using enable not disable) to stop suppressing.

Note that disabling for a single line uses the # pylint syntax while disabling for this line onward uses the # pragma pylint syntax. These are easy to confuse especially when copying & pasting.

Putting It All Together

I usually use a mix of these approaches.

  • I use ~/.pylintrc for absolutely global standards — very few of these.

  • I use project-level pylintrc at different levels within Python modules when there are project-specific standards. Especially when you’re taking in code from another person or team, you may find they use conventions that you don’t prefer, but you don’t want to rework the code. Keeping the settings at this level helps not spread those practices to other projects.

  • I use the block style pragmas at the top of single source files. I like to turn the pragmas off (stop suppressing messages) in the heat of development even for Pylint standards I don’t agree with (like “too few public methods” — I always get that warning on custom Exception classes) — but it’s helpful to see more / maybe all Pylint messages while you’re developing. That way you can find the cases you want to address with single-line pragmas (see below), or just add comments for the next developer to explain why that warning is OK in this case.

  • I leave some of the block-style pragmas enabled even when the code is ready to check in. I try to use few of those, but when it makes sense for the module, it’s OK to do as documentation. However I try to leave as few on as possible, preferably none.

  • I use the single-line-comment style to address especially potent errors. For example, if there’s a place where it actually makes sense to do except Exception as exc, I put the # pylint: disable=broad-except on that line instead of a more global approach because this is a strange exception and needs to be called out, basically as a form of documentation.


Like everything else in Python, you can act at different levels of indirection. My advice is to think about what belongs at what level so you don’t end up with a too-lenient approach to Pylint.


回答 5

您还可以使用以下命令:

pylint --disable=C0321  test.py

我的pylint版本是0.25.1。

You can also use the following command:

pylint --disable=C0321  test.py

My pylint version is 0.25.1.


回答 6

这是一个常见问题解答

4.1是否可以在本地禁用特定消息?

是的,此功能已在Pylint 0.11中添加。这可以通过
# pylint: disable=some-message,another-one在所需的块级别或所需的代码行的末尾添加来完成。

4.2是否可以仅禁用特定模块的消息?

是的,您可以通过在文件顶部的注释中添加相应的选项来在模块级别禁用或启用(全局禁用)消息:

# pylint: disable=wildcard-import, method-hidden
# pylint: enable=too-many-lines

您可以通过以下方式禁用消息:

  • 数字ID: E1101E1102
  • 象征性讯息:no-memberundefined-variable等等。
  • 一组支票的名称。您可以使用抓住这些pylint --list-groups
  • 检查类别:CRW,等。
  • 用的所有支票all

请参阅文档(或pylint --list-msgs在终端中运行)以获取pylint消息的完整列表。该文档还提供了有关如何使用此功能的好示例

This is a FAQ:

4.1 Is it possible to locally disable a particular message?

Yes, this feature has been added in Pylint 0.11. This may be done by adding
# pylint: disable=some-message,another-one at the desired block level or at the end of the desired line of code.

4.2 Is there a way to disable a message for a particular module only?

Yes, you can disable or enable (globally disabled) messages at the module level by adding the corresponding option in a comment at the top of the file:

# pylint: disable=wildcard-import, method-hidden
# pylint: enable=too-many-lines

You can disable messages by:

  • numerical ID: E1101, E1102 etc.
  • symbolic message: no-member, undefined-variable etc.
  • the name of a group of checks. You can grab those with pylint --list-groups.
  • category of checks: C, R, W, etc.
  • all the checks with all.

See the docs (or run pylint --list-msgs in the terminal) for the full list of pylint‘s messages. The docs also provide a nice example of how to use this feature.


回答 7

您只需要添加一行即可禁用您要禁用的内容。例如

#pylint: disable = line-too-long, too-many-lines, no-name-in-module, import-error, multiple-imports, pointless-string-statement, wrong-import-order

将其添加到模块中的#1

You just have to add one line to disable what you want to disable. E.g.

#pylint: disable = line-too-long, too-many-lines, no-name-in-module, import-error, multiple-imports, pointless-string-statement, wrong-import-order

Add this at #1 in your module


回答 8

如果这对某人有帮助,则如果您使用的是Visual Studio Code,则希望该文件采用UTF8编码。为了生成文件,我pylint --generate-rcfile | out-file -encoding utf8 .pylintrc在PowerShell中运行。

In case this helps someone, if you’re using Visual Studio Code, it expects the file to be in UTF8 encoding. To generate the file, I ran pylint --generate-rcfile | out-file -encoding utf8 .pylintrc in PowerShell.


回答 9

根据pylint文档,最简单的方法是使用以下图表

  • C约定相关检查
  • R重构相关检查
  • W各种警告
  • E错误,用于代码中可能的错误
  • 如果发生错误而导致pylint无法进行进一步处理,则将导致严重后果。

因此,可以使用:

pylint -j 0 --disable=I,E,R,W,C,F YOUR_FILES_LOC

As per pylint documentation, the easiest is to use this chart:

  • C convention related checks
  • R refactoring related checks
  • W various warnings
  • E errors, for probable bugs in the code
  • F fatal, if an error occurred which prevented pylint from doing further processing.

So one can use:

pylint -j 0 --disable=I,E,R,W,C,F YOUR_FILES_LOC

回答 10

Python语法确实允许一行上有多个语句,并用分号(;)分隔。但是,将每一行限制为一个语句可以使人们在阅读程序时更容易遵循程序的逻辑。

因此,解决此问题的另一种方法是理解为什么出现了皮棉消息,并且在一行中没有放置多个语句。

是的,您可能会发现每行编写多个语句更容易,但是pylint不仅适合您,而且适用于代码的所有其他阅读器。

Python syntax does permit more than one statement on a line, separated by semicolon (;). However, limiting each line to one statement makes it easier for a human to follow a program’s logic when reading through it.

So, another way of solving this issue, is to understand why the lint message is there and not put more than one statement on a line.

Yes, you may find it easier to write multiple statements per line, however, pylint is for every other reader of your code not just you.


回答 11

您可能要尝试以下操作:

编辑“ C:\ Users \您的User \ AppData \ Roaming \ Code \ User \ settings.json”,并python.linting.pylintArgs在末尾添加以下行:

{
    "team.showWelcomeMessage": false,
    "python.dataScience.sendSelectionToInteractiveWindow": true,
    "git.enableSmartCommit": true,
    "powershell.codeFormatting.useCorrectCasing": true,
    "files.autoSave": "onWindowChange",
    "python.linting.pylintArgs": [
        "--load-plugins=pylint_django",
        "--errors-only"
    ],
}

Edit “C:\Users\Your User\AppData\Roaming\Code\User\settings.json” and add ‘python.linting.pylintArgs’ with its lines at the end as shown below:

{
    "team.showWelcomeMessage": false,
    "python.dataScience.sendSelectionToInteractiveWindow": true,
    "git.enableSmartCommit": true,
    "powershell.codeFormatting.useCorrectCasing": true,
    "files.autoSave": "onWindowChange",
    "python.linting.pylintArgs": [
        "--load-plugins=pylint_django",
        "--errors-only"
    ],
}