Perfect - Python 简体中文

Get Involed with Perfect!

Star Perfect On Github Stack Overflow Follow Perfect on Twitter Join the Perfect Slack

Swift 4.1.2 Platforms OS X | Linux License Apache PerfectlySoft Twitter Slack Status

本项目提供了一种将 Python 2.7 模块导入为服务器端 Swift 库的快速通道。

此软件包使用 Swift Package Manager 构建,是 Perfect 项目的一部分,但也可以独立运行。

请确保您已安装并激活最新的 Swift 4.1.2 工具链。

致谢

Chris Lattner 提出了一些更新建议。 感谢 @Chris。

Linux 构建说明

请确保在 Ubuntu 16.04 上安装了 libpython2.7-dev。

$ sudo apt-get install libpython2.7-dev

MacOS 构建说明

请确保已安装 Xcode 9.0 或更高版本。

快速开始

将 PerfectPython 依赖项添加到您的 Package.swift 文件中。

.package(url: "https://github.com/PerfectlySoft/Perfect-Python.git", 
	from: "3.2.0")

// on target section:
.target(
	// name: "your project name",
	dependencies: ["PerfectPython"]),

然后将两个不同的库导入到 Swift 源代码中。

import PythonAPI
import PerfectPython

在任何 Python API 调用之前,请务必通过调用 Py_Initialize() 函数来初始化库。

Py_Initialize()

导入 Python 模块

使用 PyObj 类来导入 Python 模块。 在以下示例中,Python 脚本 /tmp/clstest.py 已被导入到当前的 Swift 上下文中。

let pymod = try PyObj(path: "/tmp", import: "clstest")

访问 Python 变量

导入模块后,您可以使用 PyObj.load() 函数来访问变量值,或者使用 PyObj.save() 将新值存储到当前的 Python 变量中。

例如,如果 Python 脚本中有一个名为 stringVar 的变量。

stringVar = 'Hello, world'

那么您可以按照以下形式读取它的值。

if let str = pymod.load("stringVar")?.value as? String {
	print(str)
	// will print it out as "Hello, world!"
}

您也可以直接覆盖同一变量的值。

try pymod.save("stringVar", newValue: "Hola, 🇨🇳🇨🇦!")

注意 目前,Perfect-Python 支持 Swift 和 Python 之间的以下数据类型。

Python 类型 Swift 类型 备注
int Int
float Double
str String
list [Any] 递归地
dict [String:Any] 递归地

例如,您可以通过以下方式将 Swift String 转换为 PyObjlet pystr = "Hello".python()let pystr = try PyObj(value:"Hello")

要将 PyObj 转换为 Swift 数据类型(例如 String),也有两种方法可用:let str = pystr.value as? Stringlet str = String(python: pystr)

调用 Python 函数

PyObj.call() 方法可用于执行带有参数的函数调用。 考虑下面的 Python 代码。

def mymul(num1, num2):
	return num1 * num2

Perfect-Python 可以通过其名称(作为字符串)和参数(作为数组)来封装此调用。

if let res = pymod.call("mymul", args: [2,3])?.value as? Int {
	print(res)
	// the result will be 6
}

Python 对象类

相同的 PyObj.load() 函数有助于访问 Python 类类型,但是,应该调用以下方法 PyObj.construct() 来进行对象实例初始化。 此方法还支持参数作为 Python 对象类构造的数组。

假设有一个典型的 Python 类,名为 Person,它具有两个属性 nameage,以及一个对象方法,名为 intro()

class Person:
	def __init__(self, name, age):
		self.name = name
		self.age = age
		
	def intro(self):
		return 'Name: ' + self.name + ', Age: ' + str(self.age)

要在 Swift 中初始化这样的类对象,前两个步骤如下所示。

if let personClass = pymod.load("Person"),
    let person = personClass.construct(["rocky", 24]) {
    // person is now the object instance
  }

然后,您可以像访问普通变量和函数一样访问属性和类方法。

if let name = person.load("name")?.value as? String,
    let age = person.load("age")?.value as? Int,
    let intro = person.call("intro", args: [])?.value as? String {
      print(name, age, intro)
}

回调

考虑以下 Python 代码,您可以将函数作为参数执行,例如 x = caller('Hello', callback)

def callback(msg):
    return 'callback: ' + msg

def caller(info, func):
    return func(info)

等效的 Swift 代码没有什么特别之处,只是在使用前,将目标回调函数用作参数。

if let fun = pymod.load("callback"),
   let result = pymod.call("caller", args: ["Hello", fun]),
   let v = result.value as? String {
   		print(v)
   	// it will be "callback: Hello"
}

更多信息

有关 Perfect 项目的更多信息,请访问 perfect.org

微信公众号已上线(中文)