1

Q: is there a way to get Python to give me a warning when there is more than one definition of the same function, conflicting, etc.

(I just wasted a bit of time making edits to two different versions of the same function.)

A small example of conflicting function definitions:

$>  cat ./foo2.py
cat ./foo2.py
def foo():
    print "1st definition of foo()"
def foo():
    print "2nd definition of foo()"
foo()

Executing - Python uses the last definition. (By the way, is that officially defined? It is useful semantics, e.g. when creating functions on the fly in strings and evaling them. It is useful in an interpreter. But it masks bugs in some circumstances, hence my desire to have an optional warning.)

$>  python ./foo2.py
python ./foo2.py
2nd definition of foo()

"python -W all" doesn't give a warning:

$>  python -W all ./foo2.py
python -W all ./foo2.py
2nd definition of foo()

Neither does "use warnings".

For that matter, python3 does the same as the above (although python3 requires parens around the argument to print :-( ).

pylint DOES report the error

E:  4, 0: function already defined line 2 (function-redefined)

but I have the usual objections to separate lint tools that should be well-known to anyone familiar with the history of programming languages. (E.g. lint is noisy; lint is optional, not always run; lint is optional, e.g. was not installed automatically with python, and required me to do some hacks to get to install (homebrew problems?) - I almost gave up, and if I had given up I would not have had pylint.)

Therefore, even though pylint does find the error, I still ask:

Q: is there any way to get python itself to report an error or warning for multiply defined functions?

===

By comparison, and in response to folks who say "Why would you want to do that in a dynamic language?"

Perl is also a dynamic language. When Perl first came out, it did not have such warnings. But now it does, as people realized that such warnings are good for code quality.

Perl does not warn about multiple definitions by default, but does warn with -Wall or use warning.

$>  cat foo2.pl
cat foo2.pl
sub foo { print "foo#1" }
sub foo { print "foo#2" }
foo()

$>  perl -Wall ./foo2.pl
perl -Wall ./foo2.pl
Subroutine foo redefined at ./foo2.pl line 2.
foo
Krazy Glew
  • 7,210
  • 2
  • 49
  • 62
  • No, there isn't; Python is a very dynamic language, there's nothing to stop you reassigning the name to something else (function or otherwise). – jonrsharpe May 20 '16 at 22:26
  • This is a particular example of a warning that one might like to optionally enable, as in the more general question [does-python-have-a-use-strict-and-use-warnings-like-in-perl](http://stackoverflow.com/questions/13425715/does-python-have-a-use-strict-and-use-warnings-like-in-perl) – Krazy Glew May 20 '16 at 22:26
  • And given that the answer to that question was *"no"*, what did you expect? – jonrsharpe May 20 '16 at 22:27
  • 1
    IDEs like PyCharm will do that while you type the function. – C14L May 20 '16 at 22:28
  • @jonrsharpe: I was hoping for better. Python does not need "use warnings" for most of the stupidities of Perl. But multiply defined functions, and allowing a typo in a variable name to break your program, are two examples where Pythns immaturity is exhibited. – Krazy Glew May 20 '16 at 22:44
  • @jonrsharpe: plus, I admit that I wanted to bait the Python fanbois who say "Python doesn't need no steenking warnings because Python has fixed all the problems that made Perl need warnings" :-) – Krazy Glew May 20 '16 at 22:55
  • 2
    That is not an excellent motive. – TigerhawkT3 May 20 '16 at 22:59
  • 1
    It's also a feature, not a bug - `foo = bar(foo)` allows you to replace the function with a wrapped version for things like logging, memoization, etc. And if you make a typo, your tests will tell you that. It's not Python that's being immature... – jonrsharpe May 21 '16 at 07:36

3 Answers3

1

No, there's no way to get Python to behave this way natively. A function definition is essentially an assignment to a name, and names in Python can be reassigned at any time. Functions are not treated in any special way compared to integers, strings, etc.

kindall
  • 178,883
  • 35
  • 278
  • 309
  • 1
    Well, then, Python SHOULD have such a warning. (Expecting religious argument to ensue.) ... I will give it a few days in the hope that somebody will report that there is a way to do this, perhaps in Python3 ... but I suspect that I will mark this answer approved eventually, since Python does seem to be an immature language, lacking features such as this for code quality. – Krazy Glew May 20 '16 at 22:33
  • Fair enough. If I use Python enough for production code, I may do so. But I do get tired of language wars. – Krazy Glew May 20 '16 at 22:41
  • I can't say I have ever found this to be a problem in my Python coding. You would generally notice it pretty quickly if it happened. – kindall May 20 '16 at 22:50
  • 2
    @KrazyGlew: If you get tired of them, you should probably stop provoking them by using deliberately inflammatory language. – user2357112 May 20 '16 at 22:53
1

You can decorate all you functions and create a database of symbols and warn on redefinitions.

totoro
  • 2,469
  • 2
  • 19
  • 23
  • I have been using python introspection, but AFAIK it only reports the last definition of a function. Is there a way to make it report all definitions? // Decorating all functions would be a loss, since the purpose of such checks is to find bugs, and inexperienced programmers who are unlike to know how to decorate are most common source of such bugs. (But by no means the only...) – Krazy Glew May 20 '16 at 22:53
  • 1
    You can make a function that decorates all methods in a module. To share that information between multiple modules in a package requires some extra management. Maybe it can be done simple enough so users only need to import something and maybe call a function to find duplicates. – totoro May 20 '16 at 23:04
0

there's nothing built into the language, but you can use a code-checking tool like pylint (and I believe there are other tools), which will find these kinds of things and warn you about them.

Chris Curvey
  • 9,738
  • 10
  • 48
  • 70
  • As I added to my question: ...the usual objections to separate lint tools that should be well-known to anyone familiar with the history of programming languages. (E.g. lint is noisy; lint is optional, not always run; lint is optional, often not installed.) – Krazy Glew May 20 '16 at 22:39