Pythonの属性操作関数:hasattr、getattr、setattrの使い方

hasattr(object, name)

この関数は、指定されたオブジェクトに特定の属性が存在するかどうかを判定します。Pythonでは、属性には変数とメソッドの両方が含まれます。属性が存在すればTrueを、存在しなければFalseを返します。nameパラメータは文字列型である必要があり、変数名やメソッド名はすべて文字列形式で渡す必要があります。

class SampleClass():
    language = 'Python'
    def sample_method(self):
        return 'SampleClassのsample_methodメソッド'

hasattr(SampleClass, 'language')
# 結果: True

hasattr(SampleClass, 'version')
# 結果: False

hasattr(SampleClass, 'sample_method')
# 結果: True

getattr(object, name[, default]) この関数は、オブジェクトの属性値を取得します。属性が存在すればその値を返し、存在しない場合には2つの挙動があります。defaultパラメータが指定されていない場合、エラーが発生します。defaultパラメータが指定されている場合、オブジェクトにその属性が存在しない場合は指定されたデフォルト値が返されます。

指定された属性がメソッドの場合、関数オブジェクトが返されます。関数の戻り値を取得するには、関数オブジェクトを呼び出す必要があります。メソッドを呼び出すには、関数オブジェクトの後に括弧を追加します(例: method())。

注意点として、インスタンスメソッドの場合、getattr(ClassName, 'method')() のように直接呼び出すことはできません。インスタンスメソッドは、クラスのインスタンス化されたオブジェクトを介して呼び出す必要があります。インスタンスメソッドとクラスメソッドの違いは、インスタンスメソッドはselfを第一引数として定義され、クラスのインスタンスを介してのみ呼び出せるのに対し、クラスメソッドは@classmethodデコレータで修飾され、clsを第一引数として定義され、クラスオブジェクトを直接呼び出すことができます(インスタンス化不要)。

class SampleClass():
    language = 'Python'
    def instance_method(self):
        return 'Hello from instance method'

# 存在する属性の取得
getattr(SampleClass, 'language')
# 結果: 'Python'

# 存在しない属性の取得(エラー発生)
getattr(SampleClass, 'version')
# 結果: Traceback (most recent call last):
#   File "<pyshell#464>", line 1, in <module>
#     getattr(SampleClass, 'version')
# AttributeError: class SampleClass has no attribute 'version'

# デフォルト値の指定
getattr(SampleClass, 'version', 3.9)
# 結果: 3.9

# インスタンスメソッドの取得
getattr(SampleClass, 'instance_method')
# 結果: <unbound method SampleClass.instance_method>

# インスタンスメソッドの直接呼び出し(エラー)
getattr(SampleClass, 'instance_method')()
# 結果: Traceback (most recent call last):
#   File "<pyshell#470>", line 1, in <module>
#     getattr(SampleClass, 'instance_method')()
# TypeError: unbound method instance_method() must be called with SampleClass instance as first argument (got nothing instead)

# インスタンスを介したメソッド呼び出し
getattr(SampleClass(), 'instance_method')()
# 結果: 'Hello from instance method'


class AnotherClass(object):
    framework = 'Django'
    @classmethod
    def class_method(cls):
        return 'AnotherClassのクラスメソッド'

# クラスメソッドの呼び出し
getattr(AnotherClass, 'class_method')()
# 結果: 'AnotherClassのクラスメソッド'

setattr(object, name, value) この関数は、オブジェクトの属性に値を設定します。指定された属性が既に存在する場合、setattrはその値を指定された値に更新します。属性が存在しない場合、setattrは新しい属性をオブジェクトに作成し、指定された値を割り当てます。

class DataClass():
    title = '元のタイトル'
    def display(self):
        return f'タイトル: {self.title}'

# 既存属性の更新
setattr(DataClass, 'title', '更新されたタイトル')
getattr(DataClass, 'title')
# 結果: '更新されたタイトル'

# 新しい属性の追加
setattr(DataClass, 'version', 1.0)
getattr(DataClass, 'version')
# 結果: 1.0
class ConfigClass():
    app_name = 'MyApp'
    def run(self):
        return 'アプリケーション実行中'

# 属性が存在するか確認し、存在しない場合は設定
if not hasattr(ConfigClass, 'debug_mode'):
    setattr(ConfigClass, 'debug_mode', False)

# 設定された値の確認
getattr(ConfigClass, 'debug_mode')
# 結果: False

タグ: Python 属性操作 hasattr getattr setattr

6月1日 07:03 投稿