質問

PythonでJavaの final に相当するものに関するドキュメントが見つかりませんでした。そのようなことはありますか?

オブジェクトのスナップショットを作成しています(何かが失敗した場合の復元に使用されます)。このバックアップ変数が割り当てられたら、変更しないでください。Pythonの最終的な機能はこれに適しています。

役に立ちましたか?

解決

Javaで変数を final にすることは、基本的に、変数に割り当てた後、その変数を別のオブジェクトを指すように再割り当てできないことを意味します。実際には、オブジェクトを変更できないという意味ではありません。たとえば、次のJavaコードは完全に機能します。

public final List<String> messages = new LinkedList<String>();

public void addMessage()
{
    messages.add("Hello World!");  // this mutates the messages list
}

しかし、以下はコンパイルすらしません:

public final List<String> messages = new LinkedList<String>();

public void changeMessages()
{
    messages = new ArrayList<String>();  // can't change a final variable
}

だからあなたの質問は、Pythonに final が存在するかどうかです。ありません。

ただし、Pythonには不変のデータ構造があります。たとえば、 list を変更することはできますが、 tuple を変更することはできません。 set は変更できますが、 frozenset などは変更できません。

私のアドバイスは、言語レベルで非突然変異を強制することを心配せずに、これらのオブジェクトが割り当てられた後に突然変異するコードを書かないようにすることに集中することです。

他のヒント

Pythonには「最終」に相当するものはありません。

ただし、クラスインスタンスの読み取り専用フィールドを作成するには、を使用できますプロパティ関数。

編集:おそらく次のようなものが必要です:

class WriteOnceReadWhenever:
    def __setattr__(self, attr, value):
        if hasattr(self, attr):
            raise Exception("Attempting to alter read-only value")

        self.__dict__[attr] = value

assign-once変数は設計上の問題です。変数が一度だけ設定されるようにアプリケーションを設計します。

ただし、デザインの実行時チェックが必要な場合は、オブジェクトのラッパーを使用して実行できます。

class OnePingOnlyPleaseVassily( object ):
    def __init__( self ):
        self.value= None
    def set( self, value ):
        if self.value is not None:
            raise Exception( "Already set.")
        self.value= value

someStateMemo= OnePingOnlyPleaseVassily()
someStateMemo.set( aValue ) # works
someStateMemo.set( aValue ) # fails

それは不格好ですが、実行時に設計上の問題を検出します。

そのようなことはありません。一般に、Pythonの姿勢は「これを変更したくない場合は、変更しないでください」です。 APIのクライアントは、とにかく、ドキュメント化されていない内部構造をただぶらぶらすることはほとんどありません。

モデルの関連ビットにタプルまたは名前付きタプルを使用することで、この問題を回避できます。これらは本質的に不変です。もちろん、それはもちろん変更可能でなければならないモデルのどの部分にも役立ちません。

Pythonには「最終」に相当するものがありません。 「パブリック」はありません。および「保護」どちらも、命名規則による場合を除きます。 「束縛と規律」ではありません。

http://code.activestate.com/recipes/576527/ は、凍結機能。ただし、完全には機能しません。

ただし、単に変更可能にすることを検討します。

これは古い質問ですが、さらに別の潜在的なオプションを追加すると考えました: assert を使用して、変数が元々&#に設定されていたものに設定されていることを確認することもできます8211;必要に応じて二重チェック。これはJavaの final とは異なりますが、同様の効果を作成するために使用できます。

PI = 3.14
radius = 3

try:
    assert PI == 3.14
    print PI * radius**2
except AssertionError:
    print "Yikes."

上記のように、何らかの理由で PI 3.14 に設定されていない場合、 AssertionError がスローされるため、 try / except ブロックはおそらく賢明な追加でしょう。とにかく、状況によっては便利になる場合があります。

Pythonには実際にはfinal型がありません。タプルなどの不変型がありますが、それは別のものです。

他のいくつかの回答では、クラスを疑似最終変数でいっぱいにしているため、クラスにはいくつかのFinal型のみが含まれることが望ましいので、記述子を使用して最終型を作成することをお勧めします:

from typing import TypeVar, Generic, Type

T = TypeVar('T')

class FinalProperty(Generic[T]):
    def __init__(self, value: T):
        self.__value = value
    def __get__(self, instance: Type, owner) -> T:
        return self.__value
    def __set__(self, instance: Type, value: T) -> None:
        raise ValueError("Final types can't be set")

このクラスを次のように使用する場合:

class SomeJob:
    FAILED = FinalProperty[str]("Failed")

その後、そのクラスのインスタンスでその変数を設定することはできません。 残念ながら、WriteOnceReadWheneverの回答と同様に、クラス変数を設定できます。

job = SomeJob()
job.FAILED = "Error, this will trigger the ValueError"
SomeJob.FAILED = "However this still works and breaks the protection afterwards"
ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top