2009-12-09 4 views
8

このテーマはしばらく私を邪魔しています。 my Python projectについては異なるバージョンのPythonをサポートしています

私はPythonのバージョン3.1から2.4をサポートできるようにしたかったです。私はこれをどうやって行うのかと思って、最終的にPythonの4つの異なるバージョン(2.4、2.5、2.6、3.1)のソースコードを4つの別々のフォークにすることに決めました。

私が主な理由は、私は今の代わりに1の4倍にしなければならないPythonの配布厄介の、悪い決定としてそれを見るようになってきています。

質問は、どうしたらいいですか?

私のプロジェクトは科学計算分野です。 Python 2.4に依存している人がまだたくさんいるという印象を受けました。

誰かが私のプロジェクト全体を2.4用に書きましたが、それは私には受け入れられません。それは私がコンテキストマネージャーを使用することができないことを意味し、それは私があきらめないものです。

通常のPythonプロジェクトはどのように2.4をサポートしていますか?コンテキストマネージャの使用を避けますか?

また、Python 3.1用に別のフォークを持っていますか? 2.xや3.xで同じコードを実行するためのあらゆる種類のハックがあることは知っていますが、Pythonが好きな理由の1つは、コードが美しいからです。互換性ハッキングでは醜いことは許されません。

お願いします。

答えて

1

はい、同じコードベースで2.4 - 2.7のすべてをサポートするには、Python 2.4の構文を記述する必要があります。

それは少し簡単3.xのと互換性のあるコードを書くために作るためにはPython 2.6と2.7の目標のいくつかの変更は、しかし、あなたは2.5のサポートをドロップすると、以下のことをしなければなりません。

+0

です。私は同じコードベースでそれをやっていないというオプションを探しています。実際、これは私が今やっていることです。極端に、異なるバージョンのフォークを別々に持っています。多分私はそれをよりスマートにすることができたかもしれない。 –

0

バージョンの違いが極端でない場合、あなたは適応層として機能するバージョン固有のコードを記述している別のパッケージまたはモジュールにそれらを分離してみてください。

簡単なやり方では、新しいバージョンのPythonが、(例えば)simplejsonのように、以前は標準であったパッケージを標準とするような、単純なケースで別のモジュールを使わなくても可能です。あなたはそれをすべて収集する必要がありますので、あなたは、あなたのコードベース全体にランダムに散らばっようなことを望んでいないだろう、そのようなあなたはおそらく持っているものとして、非自明なもののため

try: 
    import simplejson as json 
except ImportError: 
    import json 

:我々はいくつかのコードでは、これに似た何かを持っています可能な場合は1か所にまとめて、バージョン固有のコードの唯一のセクションにします。

コンテキストマネージャを使用したいというコメントなど、構文が異なるものではうまく動作しません。確かに、別のモジュールにコンテキストマネージャコードを置くことができますが、それはおそらくそれを使用する場所を複雑にします。そのような場合には、このアダプター・モジュールに対して特定の重要な機能(コンテキスト・マネージャーはやや簡単にシミュレートできると思われる)をバックポートする可能性があります。

間違いなく別のコードベースを使用することは、最悪のことですので、私はそれを避けることをお勧めします。少なくとも、新しいバージョンのPythonの機能を任意に使用しないでください。特定の論理ブロックを簡略化するコードではうまく見えるかもしれませんが、そのロジックを複製する必要があります。コードベースは、たとえ1つのモジュールであっても、利益を無効にする以上のものになります。

レガシーコード用の古いバージョンを使用しています。新しいリリースではサポートされるようになりましたが、以前のバージョンのサポートを維持しています。ある時点で、コードのメジャーリリースがスケジュールに現れ、古いPythonのサポートを中止するかどうかを検討します。それが起こると、私たちは2.4から2.6へ直接移行していくつかのバージョンを飛ばしようとし、新しい構文と非適合機能を実際に利用し始めます。

0

まず最初に、Python 2.xは主に下位互換性のある同じ構文を共有していることを覚えておく必要があります。新機能&を追加します。考慮しなければならないことは、必ずしも間違いではないことです。有害ではありませんが、混乱を招く恐れがあります。

Python 3.xは設計上後方互換性があり、すべての旧式のひらめきを残す予定です。 Python 2.6では、移行を容易にするためにPython 3.xにも多くの変更が導入されています。それらのすべてを見るには、What's New in Python 2.6文書を読むことをお勧めします。このため、Python 2.6でPython 3.1でも動作するコードを記述することは可能ですが、注意点はありません。

でも、多くの小さなコード変更がありますが、多くのコードをtry/exceptブロックにラップする必要があります.2つのバージョン間でも、 .xと3.xブランチは完全に可能です。私はあなたがあなたがしたいことをするためにあなたのオブジェクトの多くの属性とタイプテストをしていることに気付くでしょう。

さまざまなPythonバージョンをサポートする主要プロジェクトのコードをチェックアウトすることをお勧めします。 Twisted Matrixが最初に思い浮かぶのです。そのコードは、Pythonコードをどのように記述するべきかの素晴らしい例です。

最後に、あなたがするべきことは簡単ではないので、多くの作業の準備をしてください!

+0

2.4-2.6の異なるブランチはどこにありますか?私はWindows用に異なるバイナリダウンロードを見ましたが、ソースは1つのフォルダのようです。私は何かが欠けていたか? –

+0

'set'と' frozenset'が** Python 2.4 **に追加されました。 http://www.python.org/doc/2.4.4/whatsnew/whatsnew24.html – u0b34a0f6ae

+0

@ cool-RR - いいえ、私は何かを見逃していました。私は悪い情報を削除しました。 @ kaizer.se - ありがとう、私は組み込みの型の追加と 'sets'モジュールの非推奨を混同していました。 – jathanism

1

あなたの問題とは異なる回答があるようです。まず

、あなたはすべての Pythonのバージョンは[はい、あなたはおそらく可能な最小の機能のサブセットを使用して立ち往生しているためすべての機能を提供したい場合は - それゆえのPython 2.4のためにあなたのコードを書きます。あるいは、純粋なPythonであれば、より新しいインタープリターのフィーチャーをバックポートすることもできます(コンテキストマネージャーやコルーチンの場合ではありません)。

バージョンサポートを機能に分割することができます。コンテキストマネージャーから大きな利益を得る機能(オプション)があると思われる場合は、別のモジュールで利用できるようにして、2.4ユーザーと言うことができますその機能はありません。

Python 3をサポートするには、2to3ヘルパーを見てください。コードを正しく書くと、2つの別々のコードベースを維持する必要はありません。

0

virtualenvを試して、単一のPythonバージョンを使用してアプリケーションを配布することができます。しかし、これはあなたの場合には実用的かもしれません。

0

関連する問題があります。これは、jythonとcpythonの両方を2.4に戻す大きなシステムです。基本的には、書かれる必要があるコードをうまくいけば小さなモジュールに分離し、条件付きでインポートする必要があります。

# module svn.py 
import sys 
if sys.platform.startswith('java'): 
    from jythonsvn import * 
else: 
    from nativesvn import * 

この例では、おそらくsys.version_infoに対してテストを使用します。あなたがのように使用することは、ユーティリティモジュールにいくつかの簡単なものを定義することができます。import utilのから*

# module util.py 
import sys 
if sys.exc_info[0] == 2: 
    if sys.exc_info[1] == 4: 
     from util_py4 import * 
    ... 

その後のようなutil_py4.pyで物事:

def any(seq):    # define workaround functions where possible 
    for a in seq: 
     if a: return True 
    return False 
... 

をこれよりも別の問題であるが、 (あなたがサポートを続けたいので)、このリンクはいくつかの役に立つガイダンスを提供しています(他にもPython 2.xの移植に関するさまざまな記事があります)。

コンテキストマネージャなしでは生きられないあなたのコメントは少し混乱します。 コンテキストマネージャは強力であり、コードを読みやすくしてエラーのリスクを最小限に抑えますが、2.4バージョンのコードではコードを持つことができません。

### 2.5 (with appropriate future import) and later 
with open('foo','rb')as myfile: 
    # do something with myfile 

### 2.4 and earlier 
myfile = None 
try: 
    myfile = open('foo','rb') 
    # do something with myfile 
finally: 
    if myfile: myfile.close() 

2.4をサポートしたいので、2番目の構文を持つだけのコードが必要です。両方の方法で書くのは本当にエレガントでしょうか?