Backporting Python 3 open (encoding = "utf-8") in Python 2

I have a Python code base created for Python 3 that uses the Python 3 open () style with an encoding parameter:

https://github.com/miohtama/vvv/blob/master/vvv/textlineplugin.py#L47

with open(fname, "rt", encoding="utf-8") as f: 

Now I would like to back up this code in Python 2.x, so that I will have a code base that works with Python 2 and Python 3.

What is the recommended strategy for dealing with open() differences and the lack of an encoding parameter?

Can I have a Python 3 open() style file handler that passes threads, so it will act like Python 2 open() ?

+141
Jun 10 2018-12-18T00:
source share
5 answers

1. To get the encoding parameter in Python 2:

If you only need to support Python 2.6 and 2.7, you can use io.open instead of open . io is the new io subsystem for Python 3, and it also exists in Python 2.6 and 2.7. Remember that in Python 2.6 (as well as in 3.0) it is implemented exclusively in python and is very slow, so if you need file reading speed, this is not a good option.

If you need speed or need support for Python 2.5 or earlier codecs.open , you can use codecs.open . It also has an encoding parameter and is very similar to io.open except that it handles line endings differently.

2. To get a Python 3 open() -style file handler that passes string streams:

 open(filename, 'rb') 

Note the โ€œb,โ€ which means binary.

+164
Jun 11 '12 at 6:32
source share

I think,

 from io import open 

.

+60
Jun 10 2018-12-18T00:
source share

Here is one way:

 with open("filename.txt", "rb") as f: contents = f.read().decode("UTF-8") 
+18
Nov 17 '16 at 15:38
source share

This can do the trick:

 import sys if sys.version_info[0] > 2: # py3k pass else: # py2 import codecs import warnings def open(file, mode='r', buffering=-1, encoding=None, errors=None, newline=None, closefd=True, opener=None): if newline is not None: warnings.warn('newline is not supported in py2') if not closefd: warnings.warn('closefd is not supported in py2') if opener is not None: warnings.warn('opener is not supported in py2') return codecs.open(filename=file, mode=mode, encoding=encoding, errors=errors, buffering=buffering) 

Then you can save the code in the python3 path.

Please note that some APIs like newline , closefd , opener do not work

+8
Nov 21 '14 at 10:13
source share

If you use six , you can try this using the latest Python 3 API and can work as in Python 2/3:

 import six if six.PY2: # FileNotFoundError is only available since Python 3.3 FileNotFoundError = IOError from io import open fname = 'index.rst' try: with open(fname, "rt", encoding="utf-8") as f: pass # do_something_with_f ... except FileNotFoundError: print('Oops.') 

And, giving up Python 2 support is simply removing everything related to six .

+1
Jun 10 '19 at 4:51
source share



All Articles