下面是一些与 Rust 相关的工具和库的介绍:
Cargo:
Cargo 是 Rust 的包管理工具和构建系统。它能够自动管理 Rust 项目的依赖关系,并提供命令行工具来构建、测试和运行项目。Cargo 简化了 Rust 项目的创建和管理过程,使得开发者可以更专注于编写代码而不用过多关注构建细节。
Clippy:
Clippy 是 Rust 的静态代码分析工具,它能够检测出一些潜在的代码问题和不良习惯,并给出相应的建议。Clippy 可以帮助开发者编写更规范、更高质量的 Rust 代码。
Rust 文档(Rust Docs):
Rust Docs 是 Rust 官方提供的文档工具,用于生成和浏览 Rust 标准库和第三方库的文档。它为 Rust 开发者提供了一个方便的方式来查阅和学习 Rust 相关的文档。
Rust 标准库(Rust Standard Library):
Rust 标准库是 Rust 语言的核心库,它提供了许多常用的数据结构、算法和系统调用等功能。开发者可以直接使用标准库中的类型和函数,以快速构建高效、安全的 Rust 程序。
Rust 编译器(rustc):
Rust 编译器是将 Rust 代码编译为可执行文件或库的工具。它负责解析、类型检查、代码生成等编译过程,并生成适应目标平台的机器码。Rust 编译器是 Rust 语言的核心组件之一,它实现了 Rust 语言规范,并负责将 Rust 代码转化为可执行的程序。
这些工具和库都是 Rust 生态系统中重要的组成部分,它们与 Rust 的设计理念和目标相辅相成,使得开发者能够更加高效地编写、测试和维护 Rust 项目。无论是初学者还是有经验的开发者,对于这些工具的了解和使用都能够提升开发效率和代码质量。
Cargo 是 Rust 的官方构建工具和包管理器。它用于帮助开发者构建、测试和管理 Rust 项目,简化了项目的依赖管理、构建配置和发布流程。下面详细介绍一下 Cargo 的主要功能和用法:
创建项目: 使用 Cargo 可以快速创建一个新的 Rust 项目。通过运行 cargo new
命令,在当前目录下生成一个新的项目文件夹,并自动生成了一个简单的目录结构和必要的文件,包括 Cargo.toml
、src/main.rs
等。
依赖管理: Cargo 管理 Rust 项目的依赖关系。在项目的 Cargo.toml
文件中,可以指定项目所需要的外部依赖库及其版本。当构建项目时,Cargo 会自动下载并编译这些依赖库,并将其集成到项目中。可以使用 cargo build
命令来构建项目并处理依赖关系。
构建项目: Cargo 提供了简洁的命令行接口,可以用于构建 Rust 项目。运行 cargo build
命令将会编译项目的源代码,并生成可执行文件或库文件。Cargo 会根据项目的依赖关系自动解析和编译相关的代码。
运行项目: 使用 cargo run
命令可以方便地运行 Rust 项目。Cargo 会自动编译项目并执行生成的可执行文件。如果项目是一个库,可以使用 cargo test
命令来运行项目中的测试用例。
测试项目: Cargo 提供了内置的测试框架和命令,用于编写和运行测试用例。在项目中的 src
目录下创建一个名为 tests
的子目录,并在其中编写测试用例。然后使用 cargo test
命令运行测试,并查看测试结果。
发布项目: 使用 Cargo 可以方便地发布 Rust 项目。通过运行 cargo build --release
命令,Cargo 会进行优化编译,生成一个发布版本的可执行文件。然后可以将生成的可执行文件部署到生产环境中。
文档生成: Cargo 提供了文档生成工具,可以生成项目的文档。在项目中的注释中添加文档注解,并使用 cargo doc
命令生成文档。生成的文档会包含项目的结构、函数、模块等信息,并可以通过浏览器进行查看。
更新依赖: 当项目依赖的库有新的版本发布时,可以使用 Cargo 更新依赖关系。运行 cargo update
命令,Cargo 会检查项目的依赖关系,并下载最新的版本。
除了上述功能,Cargo 还提供了其他一些辅助功能,例如初始化 Git 仓库、自动下载编译工具链(Rustup)、发布到 Cargo 社区等。这些功能使得 Cargo 成为 Rust 开发中必不可少的工具,极大地简化了项目的管理和构建过程,提高了开发效率。
在 macOS 上配置 Rust 环境,可以按照以下步骤进行:
安装 Homebrew(如果未安装):
打开终端,并执行以下命令来安装 Homebrew:
/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
安装 Rust 编程语言:
在终端中执行以下命令来安装 Rust:
curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh
这将下载并运行 Rust 安装脚本。
配置环境变量:
安装完成后,脚本会提示你将 Rust 相关的可执行文件路径添加到环境变量中。请按照提示选择「2」或输入「2」,然后按 Enter 键。
初始化 Rust 环境:
执行以下命令初始化 Rust 环境:
source $HOME/.cargo/env
验证安装:
在终端中执行以下命令验证 Rust 是否成功安装:
rustc --version
cargo --version
安装 wasm-pack:
这将下载并执行 wasm-pack 安装脚本。根据提示,可能需要输入管理员密码来完成安装。
curl https://rustwasm.github.io/wasm-pack/installer/init.sh -sSf | sh
wasm-pack --version
如果以上步骤没有出现任何错误,那么你的 macOS 系统上已成功配置了 Rust 环境。你可以开始使用 Rust 编程语言进行开发了。需要注意的是,Rust 包管理器 Cargo 也已经安装好了,它可以帮助你管理 Rust 项目的依赖和构建过程。
希望上述步骤能够帮助到你顺利配置 Rust 环境。如果在安装过程中遇到任何问题,你可以参考 Rust 官方文档 或 Rust 社区中的相关资源来获取更多帮助。
当在 VS Code 中配置 Rust 开发环境时,以下是几个常用的插件推荐:
rust-analyzer:这是官方提供的 Rust 插件,是一个功能强大的 Rust 语言服务器,它提供了智能代码补全、重构建议、错误检查等高级功能。
Crates by serayuzgur:这个插件提供了对 Cargo.toml 和 Cargo.lock 文件的支持,可以方便地查看和管理项目的依赖关系。
CodeLLDB by Vadim Chugunov:如果你需要在 VS Code 中进行 Rust 代码的调试,这个插件可以与 LLDB 调试器集成,提供了强大的调试功能。
Better TOML by bungcip:这个插件提供了对 TOML 文件的语法高亮和格式化支持,对于编辑 Cargo.toml 文件来说非常实用。
Rusty Code by matklad:Rusty Code 插件提供了代码格式化、自动导入缺失的模块、错误检查等功能,帮助减少开发中的一些常见错误。
以上这些插件可以为你提供更好的 Rust 开发体验,使得在 VS Code 中编写、调试和管理 Rust 项目更加便捷和高效。可以通过在 VS Code 中搜索插件名称并安装来开始配置 Rust 开发环境。同时,也可以根据自己的需求和喜好,探索其他的 Rust 插件。
Rust 项目通常遵循一种常见的目录结构,该结构有助于组织代码、资源文件和构建工具。以下是一个常见的 Rust 项目目录结构示例:
myproject/
├── src/
│ └── main.rs
├── Cargo.toml
└── Cargo.lock
让我们逐个解释每个目录和文件的作用:
src/
:这是存放 Rust 源代码的目录。你可以在此目录下创建多个 .rs
文件来组织你的代码。通常,你会在 src/
目录下创建一个 main.rs
文件,其中包含项目的入口点。
main.rs
:这是包含项目入口点(例如 main
函数)的 Rust 源代码文件。它是 Rust 程序的起点,负责启动应用程序的执行流程。
Cargo.toml
:这是 Rust 项目的配置文件,使用 Toml 格式来描述项目的依赖项、构建选项和其他元数据。你可以在 Cargo.toml
中指定项目名称、版本号、作者信息等。
Cargo.lock
:这是由 Cargo 自动生成的锁定文件。它记录了实际使用的依赖项及其确切版本,以确保在后续构建中使用相同的依赖项版本。
除了上述基本结构之外,Rust 项目通常还包括其他目录和文件:
tests/
:如果你的项目包含测试代码,通常会在此目录下创建测试文件。测试代码用于验证项目中各个部分的正确性。
examples/
:如果你想提供一些示例用法或演示代码,可以将其放置在此目录下。
target/
:这是 Cargo 自动生成的目录,在构建过程中存储目标文件和编译生成的二进制可执行文件。
build.rs
:这是一个可选的构建脚本文件,使用 Rust 代码编写。它允许你在构建过程中自定义一些操作,例如生成代码、配置构建选项等。
其他自定义目录:根据项目的需要,你可能还会创建其他自定义的目录,用于存放静态资源文件、模板文件、配置文件等。
请注意,Rust 的目录结构没有强制要求,你可以根据项目的需求进行调整和扩展。上述目录结构只是一个常见的约定,大多数 Rust 项目都遵循类似的结构来提供一致性和易于理解的代码组织方式。
Cargo.toml
是 Rust 项目的配置文件,用于指定项目的元数据、依赖项和构建选项。它使用 Toml 格式(Tom’s Obvious, Minimal Language)编写,是一种易于理解和编辑的简单配置语言。要详细了解Cargo请阅读manifest。
下面是一个典型的 Cargo.toml
示例:
[package]
name = "myproject"
version = "0.1.0"
edition = "2021"
[dependencies]
crate1 = "1.0"
crate2 = { version = "2.0", features = ["feature1", "feature2"] }
[build-dependencies]
build_crate = "1.0"
让我们逐个解释每个部分的含义:
[package]
: 这个部分用于指定项目的元数据信息。
name
:指定项目的名称。version
:指定项目的版本号。edition
:指定 Rust 的版本。支持的选项有 "2015"
、"2018"
和 "2021"
。[dependencies]
: 这个部分用于指定项目的依赖项。你可以列出项目所依赖的外部库或 crate,并指定它们的版本信息。
crate1 = "1.0"
:这表示项目依赖名为 crate1
的 crate,并指定其版本为 1.0
。crate2 = { version = "2.0", features = ["feature1", "feature2"] }
:这表示项目依赖名为 crate2
的 crate,并指定其版本为 2.0
,同时启用其中的一些特性。[build-dependencies]
: 这个部分用于指定项目构建过程中所需要的依赖项。这些依赖项只在构建过程中使用,而不会包含在最终的二进制可执行文件中。
除了上述常见的部分之外,Cargo.toml
文件还支持其他配置选项,如:
workspace
:用于同时管理多个相关的 Rust 项目。features
:用于定义和启用 crate 的不同功能特性。target
:用于指定特定的目标平台和相关设置。patch
:用于修复或替换依赖项的特定版本。你可以根据项目的需求自定义 Cargo.toml
文件,添加适当的依赖项、配置选项和元数据信息。Rust 的构建工具 Cargo 将根据 Cargo.toml
中的配置来下载和管理依赖项,并执行相应的构建操作。
希望这个介绍对你有所帮助!如果还有其他问题,请随时提问。
Cargo 是 Rust 的官方构建工具和包管理器,提供了许多命令用于构建、测试、管理和发布 Rust 项目。以下是 Cargo 的常用命令列表:
cargo new
:创建一个新的 Rust 项目。
cargo build
:构建项目,编译源代码并处理依赖关系。
cargo run
:运行项目,编译并执行生成的可执行文件。
cargo test
:运行测试用例。
cargo bench
:运行基准测试。
cargo doc
:生成项目文档。
cargo clean
:清理项目构建产生的临时文件和目录。
cargo update
:更新项目的依赖库。
cargo init
:初始化当前目录为一个 Rust 项目。
cargo check
:检查代码是否可以成功编译,但不生成可执行文件。
cargo fix
:自动修复一些编译警告和错误。
cargo publish
:发布项目到 crates.io,Rust 社区的包管理平台。
cargo install
:安装一个二进制包程序到系统路径。
cargo uninstall
:卸载一个已安装的二进制包程序。
cargo package
:生成一个用于发布的压缩包。
cargo metadata
:显示项目的元数据信息,依赖关系等。
cargo fmt
:格式化源代码。
cargo clippy
:运行 Clippy(Rust 的 lint 工具)对代码进行静态分析。
cargo doc --open
:生成文档并在浏览器中打开。
cargo build --release
:生成发布版本的可执行文件。
cargo build --target
:指定目标平台进行构建。
cargo build --features
:启用指定的特性进行构建。
cargo build --no-default-features
:禁用默认特性进行构建。
cargo build --all
:构建项目及其所有依赖。
cargo build --workspace
:在工作区中构建所有子项目。
cargo build --lib
:只构建项目中的库文件。
cargo build --bin
:只构建指定名称的可执行文件。
cargo build --example
:只构建指定名称的示例程序。
cargo build --tests
:只构建项目中的测试目标。
cargo build --benches
:只构建项目中的基准测试目标。
cargo build --target-dir
:指定构建输出的目录。
cargo build --all-features
:启用所有特性进行构建。
cargo build --no-default-runtime
:禁用默认运行时(仅适用于编写运行时的 Crate)。
cargo test -- --test-threads=
:设置并发运行测试的线程数。
cargo test --
:只运行与指定模式匹配的测试。
cargo test -- --ignored
:运行被标记为 #[ignore]
的测试。
cargo test --release
:以发布模式运行所有测试。
cargo doc --no-deps
:生成项目文档,但不包含依赖库的文档。
cargo run --
:在编译并运行项目时传递参数。
cargo check --all-targets
:检查项目及其所有目标的代码是否可以成功编译。
cargo fix --edition
:自动升级代码到指定的 Rust 版本。
cargo fix --allow-dirty
:允许在 Git 工作目录中运行 cargo fix
。
cargo publish --dry-run
:发布前进行 dry-run,检查是否有错误。
cargo publish --allow-dirty
:允许在 Git 工作目录中运行 cargo publish
。
cargo install
:安装指定的 Crate。
cargo install-update
:更新指定的 Crate。
cargo uninstall
:卸载指定的 Crate。
cargo search
:在 crates.io 中搜索包。
cargo clean --package
:清理指定的 Package。
cargo metadata --format-version
:指定元数据格式的版本。
这些是常用的 Cargo 命令,可以帮助你管理 Rust 项目的构建、测试、文档生成、依赖管理和发布等任务。你可以通过在命令行中输入 cargo --help
来查看更多命令以及它们的详细使用说明。
要开始你的第一个 Rust “Hello, World!” 项目,按照以下步骤进行:
安装 Rust 编程语言:首先,确保您已在计算机上安装了 Rust。可以访问 Rust 官方网站,按照指示下载并安装 Rust。
创建新项目:打开终端或命令提示符,导航到要创建项目的目录,并运行以下命令来创建一个新的 Rust 项目:
cargo new hello_world
这将在当前目录下创建一个名为 “hello_world” 的新目录,并自动生成一些初始代码。
进入项目目录:运行以下命令以进入新创建的项目目录:
cd hello_world
编辑代码:使用你喜欢的文本编辑器打开 src/main.rs
文件,并将以下代码复制粘贴到文件中:
fn main() {
println!("Hello, World!");
}
构建和运行项目:返回终端或命令提示符,运行以下命令来构建和运行你的项目:
cargo run
Rust 的构建系统 Cargo 将编译项目并运行生成的可执行文件。你应该会在终端上看到输出 “Hello, World!”。
恭喜!你已经成功创建并运行了你的第一个 Rust “Hello, World!” 项目。从这个简单的示例开始,你可以继续学习和探索 Rust 编程语言的更多方面。
Rust 可以与 Web 进行交互,使你能够构建 Web 应用程序、API 和后端服务。下面是一些可以帮助你在 Rust 中进行 Web 交互的常见方法:
Web 框架:使用 Rust 的 Web 框架可以简化 Web 开发过程,并提供路由、请求处理、中间件等功能。一些流行的 Rust Web 框架包括 Rocket、Actix-web 和 Warp。
HTTP 客户端和服务器:Rust 提供了多个库用于构建 HTTP 客户端和服务器。例如,reqwest 是一个常用的 HTTP 客户端库,hyper 是一个强大的 HTTP 服务器库。
数据库访问:与 Web 相关的应用程序通常需要与数据库进行交互。Rust 提供了各种数据库连接库和 ORM(对象关系映射)工具,例如 Diesel、sqlx 和 rusqlite。
模板引擎:用于生成动态 HTML 页面的模板引擎在 Web 开发中非常有用。Rust 中一些流行的模板引擎包括 Tera 和 Handlebars。
WebAssembly(Wasm):Rust 具备编写 WebAssembly 模块的能力,这使得你可以在 Web 浏览器中运行原生速度的 Rust 代码。你可以使用 wasm-bindgen 和 wasm-pack 工具来构建和集成 Rust 和 JavaScript 之间的接口。
WebSocket:Rust 提供了用于 WebSocket 通信的库,如 tokio-tungstenite 和 actix-web 的 WebSocket 功能。
以上只是一些在 Rust 中进行 Web 交互的方法示例,你可以根据具体需求选择合适的库和工具。Rust 社区拥有丰富的资源和文档,可以帮助你深入了解和学习 Rust 的 Web 开发。
以下是一个使用 Rust 和 WebAssembly(Wasm)进行交互的示例:
首先,确保你已经安装了 Rust 和 wasm-pack 工具。
创建新的 Rust 项目:
打开终端或命令提示符,导航到要创建项目的目录,并运行以下命令来创建一个新的 Rust 项目:
cargo new wasm_example
cd wasm_example
添加依赖:
在项目的根目录中,打开 Cargo.toml
文件,并添加以下代码来添加 wasm-bindgen 和 js-sys 的依赖:
[lib]
crate-type = ["cdylib"]
[dependencies]
wasm-bindgen = "0.2"
js-sys = "0.3"
编写 Rust 代码:
打开 src/lib.rs
文件,并使用以下代码替换其中的内容:
use wasm_bindgen::prelude::*;
#[wasm_bindgen]
extern "C" {
#[wasm_bindgen(js_namespace = console)]
fn log(s: &str);
}
#[wasm_bindgen]
pub fn greet(name: &str) {
let message = format!("FromRust, {}!", name);
log(&message);
}
上述代码定义了一个 greet
函数,它接受一个字符串参数,并在控制台输出问候消息。
生成 Wasm 模块:
在终端中运行以下命令来生成 Wasm 模块:
wasm-pack build --target web
这将使用 wasm-pack 工具将 Rust 代码编译为 WebAssembly 模块,并生成与 JavaScript 交互的必要代码。
创建 HTML 文件:
在项目的根目录中,创建一个名为 index.html
的文件,并使用以下代码填充它:
DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>WebAssembly Exampletitle>
<script type="module">
import init, { greet } from './pkg/wasm_example.js';
async function run() {
await init();
greet("Alice");
}
run();
script>
head>
<body>
body>
html>
上述代码导入了生成的 wasm_example.js
文件,并在页面加载完成后调用 greet
函数。
启动本地服务器:
在终端中运行以下命令来启动一个简单的本地服务器:
python -m http.server
运行示例:
打开浏览器并访问 http://localhost:8000
,然后打开浏览器的控制台。你应该会看到控制台输出了 “Hello, Alice!”。
通过上述步骤,你可以在 Rust 中创建一个简单的 WebAssembly 模块,并与 JavaScript 进行交互。你可以根据需要扩展这个示例,并使用更多的 Rust 函数与 JavaScript 进行交互。
当你想要在 Android 平台上使用 Rust 与 Java 进行交互时,下面是一些具体的步骤和工具可以帮助你实现这一目标:
使用 JNI(Java Native Interface):JNI 提供了一种方式,使得 Java 和本地代码能够进行交互。你可以使用 Rust 编写本地代码,并通过 JNI 接口与 Android 的 Java 代码进行通信。为了在 Rust 中与 JNI 交互,你可以使用 jni
或 rust-jni
等库来编写相应的绑定代码。
需要完成的步骤:
.so
文件)。使用 NDK(Native Development Kit):NDK 允许你使用 C、C++ 或其他本地语言来开发 Android 应用程序。你可以使用 Rust 作为 C 或 C++ 的替代语言,并在 NDK 中构建包含 Rust 代码的本地库。然后,你可以使用 Java 代码通过 JNI 调用这些本地库。
需要完成的步骤:
.so
文件)。使用 FFI(Foreign Function Interface):FFI 允许不同语言之间进行函数调用和数据传递。你可以使用 Rust 的 FFI 功能,将 Rust 函数暴露给其他语言,比如 Java。通过这种方式,你可以在 Android 的 Java 代码中直接调用 Rust 函数。
需要完成的步骤:
#[no_mangle]
和 extern
关键字将函数标记为可供外部调用。使用 rust-android-gradle
插件:rust-android-gradle
是一个方便的工具,可用于将 Rust 代码集成到 Android 项目中。它可以自动处理 Rust 代码的构建和链接,并与 Gradle 构建系统集成。
需要完成的步骤:
rust-android-gradle
插件的依赖。请注意,在实施任何方法之前,你需要确保已经按照相应工具和库的文档进行了正确的配置和设置。每种方法都有其优势和适用场景,因此根据需求选择最适合你的方法。
希望这些详细的步骤能够帮助你更好地理解 Rust 与 Android 的交互,并实现你的项目需求。
要正确安装和配置 Android NDK,请按照以下步骤进行操作:
下载 Android NDK:访问 Android NDK 的官方网站下载适合你操作系统的最新版本。
解压缩文件:将下载的 NDK 压缩文件解压到你选择的位置。例如,你可以将其解压到 ~/android-ndk
目录下。
配置环境变量:打开终端并编辑你的 shell 配置文件(例如 ~/.bashrc
或 ~/.zshrc
)。在文件末尾添加以下行(假设你将 NDK 解压缩到了 ~/android-ndk
目录):
export ANDROID_NDK_HOME=~/android-ndk
export PATH=$PATH:$ANDROID_NDK_HOME
保存文件后执行以下命令使配置立即生效:
source ~/.bashrc
或者你也可以重新启动终端。
测试安装:在终端中运行以下命令验证是否正确安装和配置了 Android NDK:
ndk-build --version
如果成功安装并配置,将显示 NDK 版本信息。
安装交叉编译目标:运行以下命令来安装 aarch64-linux-android 目标:
rustup target add aarch64-linux-android
rustup target add arm-linux-androideabi
rustup target add armv7-linux-androideabi
rustup target add i686-linux-android
rustup target add thumbv7neon-linux-androideabi
rustup target add x86_64-linux-android
配置链接器和编译参数:创建一个名为 $HOME/.cargo
的文件夹,并在其中创建一个名为 config
的文件。在 config
文件中添加以下内容:
[target.arm-linux-androideabi]
ar = "llvm-ar"
linker = "armv7a-linux-androideabi29-clang"
[target.armv7-linux-androideabi]
ar = "llvm-ar"
linker = "armv7a-linux-androideabi29-clang"
[target.thumbv7neon-linux-androideabi]
ar = "llvm-ar"
linker = "armv7a-linux-androideabi29-clang"
[target.aarch64-linux-android]
ar = "llvm-ar"
linker = "aarch64-linux-android29-clang"
[target.i686-linux-android]
ar = "llvm-ar"
linker = "i686-linux-android29-clang"
[target.x86_64-linux-android]
ar = "llvm-ar"
linker = "x86_64-linux-android29-clang"
测试编译:现在,你可以尝试使用 Cargo 构建你的项目,并将目标设置为 Android 平台,例如:
cargo build --target aarch64-linux-android
通过按照以上步骤配置 Rust 的交叉编译环境,你应该能够开始在 Android 平台上使用 Rust 进行交叉编译了。
当使用 JNI 实现 Rust 与 Android 的交互时,可以使用以下示例来说明具体步骤。假设你希望在 Android 应用程序中调用一个计算两个整数和的 Rust 函数。
创建一个名为 rust_lib
的 Rust 项目cargo new rust_lib --lib
,并添加以下内容到 lib.rs
文件中:
#[no_mangle]
pub extern "C" fn rust_greet(name: *const c_char) -> *mut c_char {
let c_str = unsafe {
assert!(!name.is_null());
CStr::from_ptr(name)
};
let name = c_str.to_str().unwrap();
let greeting = format!("FromRust, {}!", name);
CString::new(greeting).unwrap().into_raw()
}
在 Cargo.toml
文件中添加以下内容:
[lib]
crate-type = ["cdylib"]
使用以下命令在 Rust 中构建共享库文件:
cargo build --target aarch64-linux-android
上述命令将在 target/aarch64-linux-android/debug/librust_lib.so
中生成共享库文件。
在 Android 项目中的 app
模块下的 src/main
目录中创建一个名为 jni
的文件夹,并在其中创建一个 native-lib.cpp
文件。
在 native-lib.cpp
文件中添加以下内容:
#include
#include
#include
extern "C" JNIEXPORT jstring JNICALL
Java_com_example_androidapp_MainActivity_stringFromJNI(
JNIEnv* env,
jobject /* this */,
jstring name) {
const char* nativeString = env->GetStringUTFChars(name, nullptr);
void* handle = dlopen("librust_lib.so", RTLD_LAZY);
if (!handle) {
return env->NewStringUTF("Failed to load Rust library");
}
typedef char* (*rust_greet_func)(const char*);
rust_greet_func greet = (rust_greet_func)dlsym(handle, "rust_greet");
if (!greet) {
return env->NewStringUTF("Failed to find Rust function");
}
char* result = greet(nativeString);
env->ReleaseStringUTFChars(name, nativeString);
jstring output = env->NewStringUTF(result);
free(result);
dlclose(handle);
return output;
}
要把librust_lib.so
复制到jniLibs对应的目录中。
配置cmake
app build.gradle
android {
// ...
defaultConfig {
// ...
externalNativeBuild {
cmake {
cppFlags '-std=c++17'
}
}
ndk {
abiFilters "arm64-v8a"
}
}
sourceSets {
main {
// 配置 jniLibs 文件目录
jniLibs.srcDirs = ['libs']
}
}
externalNativeBuild {
cmake {
path file('src/main/cpp/CMakeLists.txt')
version '3.22.1'
}
}
}
CMakeLists.txt
cmake_minimum_required(VERSION 3.22.1)
project("rust_jni")
add_library(${CMAKE_PROJECT_NAME} SHARED native-lib.cpp)
target_link_libraries(${CMAKE_PROJECT_NAME} android log)
在 Android 项目的 Java 类中,添加以下方法:
public class MainActivity extends AppCompatActivity {
static {
System.loadLibrary("native-lib");
}
public native String stringFromJNI(String name);
// ...
}
在 MainActivity.java
中的任何适当的方法中调用 stringFromJNI()
方法,并向其传递一个字符串参数:
String greeting = stringFromJNI("Stone " + new Date().toString());
Log.d("MainActivity", greeting);
这样,在 Android 应用程序中运行时,将调用 Rust 函数并输出日志中的问候语。
当使用 Rust 和 Android NDK 进行开发时,以下是一个详细的示例,展示如何在 Android 项目中使用 Rust 编写并调用函数。
创建 Rust 项目:
在终端中执行以下命令,创建一个名为 rust-ndk
的 Rust 项目:
cargo new rust-ndk
进入项目目录:
cd rust-ndk
添加依赖项:
打开项目中的 Cargo.toml
文件,并添加 ndk
、jni
和 libc
作为依赖项:
[lib]
crate-type = ["cdylib"]
path = "src/jni.rs"
[dependencies]
jni = "0.21.1"
创建 JNI 接口:
在项目的根目录下创建一个名为 jni.rs
的文件,并添加以下代码:
use jni::JNIEnv;
use jni::objects::{JClass, JString};
use jni::sys::jstring;
#[no_mangle]
pub unsafe extern "C" fn Java_com_example_rustndk_MainActivity_stringFromRust<'local>(mut env: JNIEnv<'local>,
_: JClass<'local>,
input: JString<'local>)
-> jstring {
let input: String = env.get_string(&input).expect("Couldn't get java string!").into();
let output = env.new_string(format!("FromRust, {}!", input)).expect("Couldn't create java string!");
output.into_raw()
}
这个例子中的 Java_com_example_rustndk_MainActivity_stringFromRust
函数是一个 JNI 方法,在字符串前面拼接一个FromRust
字符串。
构建 Rust 项目:
在终端中执行以下命令构建 Rust 项目:
cargo build --target aarch64-linux-android --release
创建 Android 项目:
使用 Android Studio 创建一个新的 Android 项目,并导航到 app/src/main
目录。
添加 Rust 动态链接库:
将生成的 .so
文件复制到 app/src/main/jniLibs
目录下(如果没有该目录则自行创建)。例如,将 ../rust-ndk/target/release/librust_ndk.so
文件复制到 app/src/main/jniLibs/arm64-v8a/
目录下。
创建 Java 类和 JNI 接口:
在 app/src/main/java/com/example/rustndk
目录下创建一个名为 MainActivity.java
的类,并添加以下代码:
package com.example.rustndk;
public class MainActivity extends AppCompatActivity {
static {
System.loadLibrary("rust_ndk");
}
private ActivityMainBinding binding;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
binding = ActivityMainBinding.inflate(getLayoutInflater());
setContentView(binding.getRoot());
// Example of a call to a native method
TextView tv = binding.sampleText;
tv.setText(stringFromRust("Stone " + new Date().toString()));
}
public native String stringFromRust(String str);
}
这个类包含了一个静态代码块,用于加载名为 rust_ndk
的动态链接库。还有一个名为 stringFromRust
的方法,用于调用 Rust 函数。
这样,在 Android 应用程序中运行时,将调用 Rust 函数并输出日志中的问候语。