如何更改RS4类属性rpy2的默认值

2024-05-23 16:32:59 发布

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

我通过以下操作在python中映射一个类RS4:

from rpy2.robjects.packages import importr
import rpy2.robjects as ro

class MapTOS4(ro.methods.RS4):
    """
    writing a child class to map to S4 reference class in python
    """
    def LoadFile(self, filename):
        """access the LoadFile method of SlicedData class"""

        return ro.baseenv['$'](self, 'LoadFile')(filename)
    
    def fileSliceSize(self):
        """access the class attribute or field""" 
        return ro.baseenv['$'](self, 'fileSliceSize')
    
mql = importr('MatrixEQTL')
data = MapTOS4(mql.SlicedData())
print(data.fileSliceSize())

在执行上述代码时,我得到了以下[1] 1000,这是预期的,因为在特定的包中,类字段/属性fileSliceSize的默认值设置为1000。但是,我正在尝试将该类属性的值重置或更改为2000

在R中,您可以通过以下简单的代码轻松完成这一任务:

data$fileSliceSize = 2000 

基于我在Python中的实现,如何实现这一点

事先非常感谢你


Tags: toimportselfdatarodeffilenameclass
1条回答
网友
1楼 · 发布于 2024-05-23 16:32:59

在R中,data$fileSliceSize = 2000操作只是一种语法糖,用于调用带有三个参数的$<-函数(对象):

library(MatrixEQTL)
data = SlicedData()

`$<-`(data, 'fileSliceSize', 2000)
# SlicedData object. For more information type: ?SlicedData
# Number of columns: 0 
# Number of rows: 0 
# Data is stored in 0 slices

与通过data$fileSliceSize访问相同的方式是一种语法糖:

`$`(data, 'fileSliceSize')
# [1] 2000

BACTICK用于转义函数名中的特殊字符-您可以使用BACTICK调用任何R函数:

`print`('text')
# [1] "text"

更多信息请参见R文档的Extract chapter

因此,在rpy2中,您可以简单地执行以下操作:

ro.baseenv['$<-'](data, 'fileSliceSize', 2000)

但是,我建议尝试一种更“pythonic”的方法(为了简洁起见省略docstrings):

from rpy2.robjects.packages import importr
import rpy2.robjects as ro


# assigning these R operators here will make the code easier to read
# and provide a (negligible in this case) performance increase.
get_r_attribute = ro.baseenv['$']
set_r_attribute = ro.baseenv['$<-']


class MapTOS4(ro.methods.RS4): 

    def __init__(self, r_obj, file_slice_size=2000): 
        super().__init__(r_obj) 
        self.file_slice_size = file_slice_size

    def load_file(self, filename):
        return get_r_attribute(self, 'LoadFile')(filename)

    @property
    def file_slice_size(self):
        return get_r_attribute(self, 'fileSliceSize') 

    @file_slice_size.setter 
    def file_slice_size(self, value): 
        set_r_attribute(self, 'fileSliceSize', value)


mql = importr('MatrixEQTL') 
data = MapTOS4(mql.SlicedData()) 
print(data.file_slice_size)
# prints 2000
data.file_slice_size = 3000
print(data.file_slice_size)
# prints 3000

# setting a value initialization:
data = MapTOS4(mql.SlicedData(), file_slice_size=4000)
print(data.file_slice_size)
# prints 4000

相关问题 更多 >