【发布时间】:2015-07-03 09:01:39
【问题描述】:
我觉得原生扩展就像库一样,您应该在尝试安装依赖于原生扩展的 gem 之前将其安装到系统上。就像ImageMagic 库一样。那是对的吗?关于原生扩展,我们还有什么需要了解的吗?
【问题讨论】:
我觉得原生扩展就像库一样,您应该在尝试安装依赖于原生扩展的 gem 之前将其安装到系统上。就像ImageMagic 库一样。那是对的吗?关于原生扩展,我们还有什么需要了解的吗?
【问题讨论】:
gem 原生扩展可能链接到需要预安装的单独库,RMagick 就是一个例子。
但是,该术语实际上仅表示“包含一些需要为您的机器编译的代码”。代码被编译和链接,因此生成的可执行文件可以是机器上的 Ruby 的required。
编写 Ruby C 或 C++ 扩展的通常原因是:
速度。对于一些 CPU 密集型任务,C 代码可以比 Ruby 快 100 倍。在这种情况下,原生扩展可以与 gem 中包含的所有 C 源代码完全独立。
已经用 C 语言编写的第三方库。在这种情况下,gem 将具有将库函数绑定到 Ruby 模块、类和方法中的 C 源代码。
您可以查看带有本机扩展的 gem 的 C 源代码,它与 Ruby 源代码一起安装。按照惯例,gem 中有一个名为ext/gem_name 的文件夹,其中包含一个Ruby 文件extconf.rb,它将信息传递给编译器(从技术上讲,它创建了一个make file)。此外,C 源文件也放在那里。
MRI Ruby 在 C 中实现为一个非常“扁平”的结构,基本上由大量 C 函数组成。这使得学习如何实现原生扩展相对容易,即使您不太了解 C。您可以阅读 Extending Ruby 1.9 作为主题介绍。
本机扩展程序可能无法安装或正常工作。 Stack Overflow 上有很多问题需要帮助解决特定的失败安装问题。常见的问题是:
缺少库。希望 gem 作者会在 README 中解释您需要预安装的内容,但并不总是很清楚。
编译器不匹配。很难测试所有目标系统,所以有时extconf.rb 中的指令在特定系统上不起作用,或者C 代码会因差异而引发警告或无法编译。在 Windows 中,除非您安装 Ruby Devkit
不适用于所有版本的 Ruby。例如,JRuby可以使用 C 原生扩展,如果它已启用但并不总是可取的 - 主题相当复杂,但通常避免混合 JRuby 和原生扩展。
李>【讨论】:
Native 扩展只是一个用 C 语言(全部或部分)编写的 gem。
它可能依赖也可能不依赖外部库,这不是一个因素。重要的是这样的 gem 需要编译并且它可能是平台相关的(有理由使用 C,对吧?也许是为了使用一些低级 OS API 或其他东西。但大多数情况下它是与图书馆)。
【讨论】:
“原生扩展”是将 Ruby gem 与机器上存在的其他一些非 Ruby 软件组件或库连接起来的粘合剂。
本机扩展不是依赖项。原生扩展通常是与非 Ruby 依赖项交互的 C 代码。
例如,使用 ImageMagic 的 gem 有一个用 C 编写的本机扩展,它与 ImageMagic 对话并代表从 Ruby gem 到 ImageMagic 的桥梁。
当您安装 gem 并编译原生扩展时,您不会编译 C 库(例如 ImageMagic),该库必须已经存在于您的系统中。您编译与 gem 捆绑在一起的 C 桥。
【讨论】:
我不是红宝石专家,所以对此持保留态度:
我相当肯定它只是一个需要安装本机(例如 C-Library)库才能工作的 gem。许多 gem 只是简单地使用 Ruby API 包装现有的 C 库。
gem 的安装将触发 C 库的下载,然后将使用 gcc 或其他编译器构建这些库。如果不支持您的系统配置,则需要将参数传递给 gem 工具以指示正确的目录等。如果运气不好,您可能需要直接更改 make 文件。
【讨论】: