Python继承和关键字参数

2024-04-25 18:56:42 发布

您现在位置:Python中文网/ 问答频道 /正文

我在为pytorch变形金刚写包装。为了简单起见,我将包括一个最小的例子。一个类父类,它将是类我的\u BERT(父类)我的\u GPT2(父类)的抽象类。由于pytorch中包含了模型\u Bert模型\u gpt2的LM模型,因此它们有许多相似的函数,因此我希望通过在Partent中编码相同的函数来最小化代码冗余。你知道吗

myu-bertmyu-gpt2基本上与模型初始化不同,一个参数传递给模型,但99%的函数以相同的方式使用这两个模型。你知道吗

问题在于接受不同参数的函数“model”:

  • 对于模型\u Bert它被定义为模型(输入\u id,masekd \u lm \u标签)
  • 对于模型\u gpt2它被定义为模型(输入\u id,标签)

最小代码示例:

class Parent():
    """ My own class that is an abstract class for My_bert and My_gpt2 """
    def __init__(self):
        pass

    def fancy_arithmetic(self, text):
        print("do_fancy_stuff_that_works_identically_for_both_models(text=text)")

    def compute_model(self, text):
        return self.model(input_ids=text, masked_lm_labels=text) #this line works for My_Bert
        #return self.model(input_ids=text, labels=text) #I'd need this line for My_gpt2

class My_bert(Parent): 
    """ My own My_bert class that is initialized with BERT pytorch 
    model (here model_bert), and uses methods from Parent """
    def __init__(self):
        self.model = model_bert()

class My_gpt2(Parent):
    """ My own My_gpt2 class that is initialized with gpt2 pytorch model (here model_gpt2), and uses methods from Parent """
    def __init__(self):
        self.model = model_gpt2()

class model_gpt2:
    """ This class mocks pytorch transformers gpt2 model, thus I'm writing just bunch of code that allows you run this example"""
    def __init__(self):
        pass

    def __call__(self,*input, **kwargs):
        return self.model( *input, **kwargs)

    def model(self, input_ids, labels):
        print("gpt2")

class model_bert:
    """ This class mocks pytorch transformers bert model"""
    def __init__(self):
        pass

    def __call__(self, *input, **kwargs):
        self.model(*input, **kwargs)

    def model(self, input_ids, masked_lm_labels):
        print("bert")


foo = My_bert()
foo.compute_model("bar")  # this works
bar = My_gpt2()
#bar.compute_model("rawr") #this does not work.

我知道我可以重写My_bertMy_gpt2类中的Parent::compute_model函数。你知道吗

但由于这两种“模型”方法如此相似,我想知道是否有一种方法可以说: 我给你三个论点,你可以用你知道的

def compute_model(self, text):
    return self.model(input_ids=text, masked_lm_labels=text, labels=text) # ignore the arguments you dont know

Tags: 函数text模型selfinputlabelsmodelthat
1条回答
网友
1楼 · 发布于 2024-04-25 18:56:42

*args**kwargs应该处理您遇到的问题。你知道吗

在代码中,您将修改compute_model以接受任意参数

def compute_model(self, *args, **kwargs):
    return self.model(*args, **kwargs)

现在参数将由不同类上的model方法定义

进行此更改时,以下各项应起作用:

foo = My_bert()
foo.compute_model("bar", "baz")
bar = My_gpt2()
bar.compute_model("rawr", "baz")

如果您不熟悉args和kwargs,它们允许您向函数传递任意参数。args将接受未命名参数并按接收顺序将其传递给函数kwargs,或者关键字arguments接受命名参数并将其传递给正确的参数。因此,以下方法也将起作用:

foo = My_bert()
foo.compute_model(input_ids="bar", masked_lm_labels="baz") 
bar = My_gpt2()
bar.compute_model(input_ids="rawr", labels="baz") 

只需注意args和kwargs的名称是没有意义的,您可以为它们命名任何名称,但典型的约定是args和kwargs

相关问题 更多 >