第七章 使用嵌入式 Python (四)
弥合 ObjectScript 和嵌入式 Python 之间的差距
由于 ObjectScript
和 Python
语言之间的差异,将需要了解一些有助于弥合语言之间差距的信息。
在 ObjectScript
方面,%SYS.Python
类允许从 ObjectScript
使用 Python
。
在 Python
方面,iris
模块允许使用 Python
中的 ObjectScript
。在 Python
中,键入 help(iris)
以获取其方法和函数的列表。
使用 Python 内置函数
builtins
包在 Python
解释器启动时自动加载,它包含语言的所有内置标识符,例如基对象类和所有内置数据类型类、异常类、函数和常量。
可以将此包导入 ObjectScript
以访问所有这些标识符,如下所示:
set builtins = ##class(%SYS.Python).Import("builtins")
Python print()
函数实际上是内置模块的一个方法,因此现在可以在 ObjectScript
中使用此函数:
USER>do builtins.print("hello world!")
hello world!
然后可以使用 zwrite
命令检查内置对象,因为它是一个 Python
对象,所以它使用内置包的 str()
方法来获取该对象的字符串表示形式。例如:
USER>zwrite builtins
builtins=5@%SYS.Python ; <module 'builtins' (built-in)> ; <OREF>
出于同样的原因,可以使用 builtins.list()
方法创建 Python
列表。下面的示例创建一个空列表:
USER>set list = builtins.list()
USER>zwrite list
list=5@%SYS.Python ; [] ; <OREF>
可以使用 builtins.type()
方法查看变量列表是什么 Python
类型:
USER>zwrite builtins.type(list)
3@%SYS.Python ; <class 'list'> ; <OREF>
有趣的是,list()
方法实际上返回了一个 Python
类对象的实例,它代表一个列表。可以使用列表对象上的 dir()
方法查看列表类具有哪些方法:
USER>zwrite builtins.dir(list)
3@%SYS.Python ; ['__add__', '__class__', '__class_getitem__', '__contains__', '__delattr__', '__delitem__',
'__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__getitem__', '__gt__',
'__hash__', '__iadd__', '__imul__', '__init__', '__init_subclass__', '__iter__', '__le__', '__len__',
'__lt__', '__mul__', '__ne__', '__new__', '__reduce__', '__reduce_ex__','__repr__', '__reversed__',
'__rmul__', '__setattr__', '__setitem__', '__sizeof__', '__str__', '__subclasshook__', 'append','clear',
'copy', 'count', 'extend', 'index', 'insert', 'pop', 'remove', 'reverse', 'sort'] ; <OREF>
同样,可以使用 help()
方法获取有关列表对象的帮助。
USER>do builtins.help(list)
Help on list object:
class list(object)
| list(iterable=(), /)
|
| Built-in mutable sequence.
|
| If no argument is given, the constructor creates a new empty list.
| The argument must be an iterable if specified.
|
| Methods defined here:
|
| __add__(self, value, /)
| Return self+value.
|
| __contains__(self, key, /)
| Return key in self.
|
| __delitem__(self, key, /)
| Delete self[key].
.
.
.
注意:可以调用 %SYS.Python
类的 Builtins()
方法,而不是将 builtins
模块导入 ObjectScript
。
标识符名称
ObjectScript
和 Python
之间命名标识符的规则是不同的。例如,Python
方法名称中允许使用下划线 (_
),实际上它被广泛用于所谓的“dunder”
方法和属性(“dunder”
是“双下划线”的缩写),例如 __getitem__
或 __class__
.要使用 ObjectScript
中的此类标识符,请将它们括在双引号中:
USER>set mylist = builtins.list()
USER>zwrite mylist."__class__"
2@%SYS.Python ; <class list> ; <OREF>
相反,IRIS
方法通常以百分号 (%
) 开头。例如 %New()
或 %Save()
。要使用 Python
中的此类标识符,请将百分号替换为下划线。如果您有一个持久类 User.Person
,以下 Python
代码行将创建一个新的 Person
对象。
>>> import iris
>>> p = iris.cls('User.Person')._New()
关键字或命名参数
Python
中的一个常见做法是在定义方法时使用关键字参数(也称为“命名参数”)。这使得在不需要时删除参数或根据名称而不是位置指定参数变得容易。例如,采用以下简单的 Python
方法:
def mymethod(foo=1, bar=2, baz="three"):
print(f"foo={foo}, bar={bar}, baz={baz}")
由于 IRIS
没有关键字参数的概念,需要创建一个动态对象来保存关键字/值对,例如:
set args={ "bar": 123, "foo": "foo"}
如果 mymethod()
方法位于名为 mymodule.py
的模块中,则可以将其导入 ObjectScript
中,然后调用它,如下所示:
USER>set obj = ##class(%SYS.Python).Import("mymodule")
USER>set args={ "bar": 123, "foo": "foo"}
USER>do obj.mymethod(args...)
foo=foo, bar=123, baz=three
由于 baz
没有传入该方法,因此默认为它分配了“三”的值。
网友评论