Reputation: 254886
The new pycharm release (3.1.3 community edition) proposes to convert the methods that don't work with the current object's state to static.
What is the practical reason for that? Some kind of micro-performance(-or-memory)-optimization?
Upvotes: 249
Views: 195669
Reputation: 1790
Rather than implementing another method just to work around this error in a particular IDE, does the following make sense? PyCharm doesn't suggest anything with this implementation.
class Animal:
def __init__(self):
print("Animal created")
def eat(self):
not self # <-- This line here
print("I am eating")
my_animal = Animal()
Upvotes: -2
Reputation: 4651
PyCharm "thinks" that you might have wanted to have a static method, but you forgot to declare it to be static (using the @staticmethod
decorator).
PyCharm proposes this because the method does not use self
in its body and hence does not actually change the class instance. Hence the method could be static, i.e. callable without passing a class instance or without even having created a class instance.
Upvotes: 328
Reputation: 379
The reason why Pycharm make it as a warning because Python will pass self as the first argument when calling a none static method (not add @staticmethod). Pycharm knows it.
Example:
class T:
def test():
print "i am a normal method!"
t = T()
t.test()
output:
Traceback (most recent call last):
File "F:/Workspace/test_script/test.py", line 28, in <module>
T().test()
TypeError: test() takes no arguments (1 given)
I'm from Java, in Java "self" is called "this", you don't need write self(or this) as argument in class method. You can just call self as you need inside the method. But Python "has to" pass self as a method argument.
By understanding this you don't need any Workaround as @BobStein answer.
Upvotes: 2
Reputation: 14251
It might be a bit messy, but sometimes you just don't need to access self
, but you would prefer to keep the method in the class and not make it static. Or you just want to avoid adding a bunch of unsightly decorators. Here are some potential workarounds for that situation.
If your method only has side effects and you don't care about what it returns:
def bar(self):
doing_something_without_self()
return self
If you do need the return value:
def bar(self):
result = doing_something_without_self()
if self:
return result
Now your method is using self
, and the warning goes away!
Upvotes: 7
Reputation: 17204
Agreed with @jolvi, @ArundasR, and others, the warning happens on a member function that doesn't use self
.
If you're sure PyCharm is wrong, that the function should not be a @staticmethod
, and if you value zero warnings, you can make this one go away two different ways:
Workaround #1
def bar(self):
self.is_not_used()
doing_something_without_self()
def is_not_used(self):
pass
Workaround #2 [Thanks @DavidPärsson]
# noinspection PyMethodMayBeStatic
def bar(self):
doing_something_without_self()
The application I had for this (the reason I could not use @staticmethod) was in making a table of handler functions for responding to a protocol subtype field. All handlers had to be the same form of course (static or nonstatic). But some didn't happen to do anything with the instance. If I made those static I'd get "TypeError: 'staticmethod' object is not callable".
In support of the OP's consternation, suggesting you add staticmethod whenever you can, goes against the principle that it's easier to make code less restrictive later, than to make it more -- making a method static makes it less restrictive now, in that you can call class.f() instead of instance.f().
Guesses as to why this warning exists:
Upvotes: 89
Reputation: 275
I think that the reason for this warning is config in Pycharm. You can uncheck the selection Method may be static in Editor->Inspection
Upvotes: 24
Reputation: 1631
I agree with the answers given here (method does not use self
and therefore could be decorated with @staticmethod
).
I'd like to add that you maybe want to move the method to a top-level function instead of a static method inside a class. For details see this question and the accepted answer: python - should I use static methods or top-level functions
Moving the method to a top-level function will fix the PyCharm warning, too.
Upvotes: 11
Reputation: 526
Since you didn't refer to self
in the bar
method body, PyCharm is asking if you might have wanted to make bar
static. In other programming languages, like Java, there are obvious reasons for declaring a static method. In Python, the only real benefit to a static method (AFIK) is being able to call it without an instance of the class. However, if that's your only reason, you're probably better off going with a top-level function - as note here.
In short, I'm not one hundred percent sure why it's there. I'm guessing they'll probably remove it in an upcoming release.
Upvotes: 4
Reputation: 41
This error message just helped me a bunch, as I hadn't realized that I'd accidentally written my function using my testing example player
my_player.attributes[item]
instead of the correct way
self.attributes[item]
Upvotes: 3
Reputation: 44092
I can imagine following advantages of having a class method defined as static one:
remaining advantages are probably marginal if present at all:
Upvotes: 9