Separate print() and println() functions

In many modern languages, print output operation is separated into two main functions:

Go lang:

package main
import "fmt"

func main() {
  fmt.Print("Hello, ")
  fmt.Println("World!")
}

Kotlin lang:

print(message)
println(message)

Rust lang:

fn main() {
  print!("message")
  println!("message")
}

Julia lang:

print("message")
println("message")

I image that in python will be like this:

print("message")
println("message")

The print function will not break any of the existing possibilities, i.e. it will keep the current structure but with this signature:

print(*args, sep=' ', end='', file=None, flush=False)

and the new println will just be a new function:

println(*args, sep=' ', end='\n', file=None, flush=False)

Could this make sense? In this way we obtain a code that speaks and is suitable for new languages such as those indicated above.
Thank you

Your proposal would break likely a majority of all Python programs ever written, simply to avoid typing print(x, end='') (because flush=False is the default for print already.)

I think this is a complete non-starter. Sorry!

9 Likes

OK! I got it.
Thanks for the explanation and your honesty!

However, I find that two separate functions are much more specific and meaningful.

(Some other languages have a printf(...) too; but thatā€™s not how we roll :slightly_smiling_face: ).

I think a modern language like Rust or Goā€¦not Cā€¦thanks for your suggest

To get pedantic, Rust has macros for print! and println!, but neither of them are functions. They basically just get translated[1] into the Rust equivalent of print(..., end="") and print(...).

If Python were to grow a macro syntax[2], itā€™d be easy to define such macros. But the print() function definitely canā€™t change this behavior because it would break the world, as @TomRitchford said.


  1. at compile time, which Python doesnā€™t haveā€¦ ā†©ļøŽ

  2. but I wouldnā€™t count on it! that PEP is probably abandoned ā†©ļøŽ

ok, I agree with that too. I know Rust and I know they are macros. I was only thinking on a syntactic level. Nothing more

@TomRitchford, It would actually break any library that uses the print function. A bit like when Python 2 went to Python 3 with the transition from Keyword to a function ā€¦

But as in Python 2, if there was a form that encapsulates the two new functions, it would not break anything.

from __future__ import new_print_function
print("message")
println("message")

new_print_function.py

def println(*args, sep=' ', end='\n', file=None, flush=False):
    ...

def print(*args, sep=' ', end='', file=None, flush=False):
    ...

@Paddy3118, I would say that my proposal was for a improvement and not for a previous, which among other things, in Python already exists. printf is a function of the C language that translates a formatting into a string in stdout. This, the current print function already provides for it:

print(string % tuple(agrs))

like this: Built-in Types ā€” Python 3.12.1 documentation

note the old in title

Having said that, I apologize if I seemed not very accurate and precise in the proposal. It is not a lack of knowledge, but I only wrote in a hurry on my cell phone after a lunch. :slight_smile:
I believe that the changes, albeit painful, can sometimes benefit even if they seem superficial. Thank you all for your precious ideas.

Yes, Go has a printf analogous to C. What makes Rust and Go modern is not the usage of these old functions.

1 Like

Itā€™s trivial to do this aliasing yourself, for example:

println = print

def print(*args, end='', **kwargs):
    return println(*args, end=end, **kwargs)

Integrating this into Python is a complete non-starter, because it would be a breaking change for an overwhelmingly large percentage of existing code (possibly requiring fixes in many places - or else a similar aliasing back the other way around!).

Python long precedes all the other languages you cite, and has no reason to be beholden to design decisions made by other people/groups later on. Pythonā€™s assumption is that people will usually want a blank line after output to a terminal, so thatā€™s the default. Aside from that, if readability is the goal, why abbreviate line?

1 Like

Go print function has no formatting placeholder.
Because this exists printf function than support C style placeholders.

fmt.Println(integer)
fmt.Printf("%v\n", integer)
fmt.Printf("%d\n", integer)

Rust ha format! macro that is used into print! and printing! macros.

I apologize in advance. I donā€™t think I forced anyone to choose anything. Personally, I have 15 years of Python development under my belt and in the last 5 I have tried and used Rust and Go. I donā€™t want to compare features, but some are more convenient than others, like the two features I mentioned.

I can understand any disagreement and thoughts contrary to mine, but I think Iā€™m in a discussion site where a person can feel free to express themselves without having to feel the weight of the obligation to think like the masses.

I apologize again if my proposal was understood as a stance, but it was intended to be a comparative idea, with no obligation towards anyone, least of all towards the Python community, of which I have been part of for years and which I respect infinitely, as the language itself.

As I said in response to @TomRitchford , I accept a negative will given the massive change in the code.

Thanks again for all precious ideas.

Your contribution is greatly appreciated. We are simply being very technical, thatā€™s all.

Python aims to keep the language clean and easy to understand. One example is avoiding this dilemma:

print("Hello world!\n") vs
println("Hello world!")

I donā€™t think thereā€™s much to apologise for here. And I donā€™t think
readers have been offended (my subjective impression).

But Python is backward compatible - the 2->3 transition was the place
for breaking changes. As youā€™re clearly aware anyway :slight_smile:

A suggestion for print, like anything already present, can extend its
features but not change them, because such a change would break
everyoneā€™s existing code.

Thereā€™s also the notion that ā€œnot every one-line function needs to be in
the stdlibā€.

Plenty of us keep personal utility libraries with things weā€™d like.
Nothing prevents you making a little eg mateo.util module with
convenient print() wrapper functions with your preferred names. Just
import them!

Cheers,
Cameron Simpson cs@cskk.id.au

1 Like

No apology needed! The reactions youā€™re seeing are not about yourself or the tone of the messages, but about the idea in itself. Itā€™s not easy to change Python, especially the language, because of multiple concerns:

  • not making the language too big
  • preserving a certain design consistency
  • preserving backward compatibility
  • etc

Ideas are easy, but serious proposals need a bit more: the proposer needs to make the case about how the new thing would work, what it would improve (new use cases, better clarity for some code patterns, elimination of possible bugsā€¦), how it fits with other Python features, whether it breaks compatibility, how to teach itā€¦

In your message in this thread, you have shown examples of other languages, but did not make a case for why it would be better for Python to have two functions instead of one.
Then people have pointed out that changing default behaviour of print is excluded, which means the idea should be adapted.

One possible argument could be: itā€™s better to have two clear names than one function with a boolean parameter.
This is a design insight that fits with Python! (I think I read GvR saying that)
Then people could reply with their thoughts about whether end is a parameter thatā€™s important enough to split print in two. This would be a true idea discussion, more fruitful than Ā«this other language has thisĀ».

Hope this helps!

9 Likes

Yes, I understood!
Thanks for your explanation!
Python is great and the community is the best, as for every language!

2 Likes

Itā€™s easy enough to write your own printf if you really want it.

def printf(fmt, *args):
print(fmt % args, end = ā€˜ā€™)

printf(ā€œLook, %s, Iā€™m writing %s code!\nā€, ā€œMumā€, ā€œCā€)

As others have noted, print by default is the proposed ā€˜printlnā€™. Not said is that perhaps 95% of print uses keep the final newline. So I think it a waste for other languages to use the longer and slightly harder to type word for the overwhelmingly most common use. Besides which, people writing test blocks, rather than lines, to files can use file.write(chars).

3 Likes

If you insist on another function, try: sys.stdout.write(...). Itā€™ll print without an auto newline.

2 Likes