This shows you the differences between two versions of the page.
Both sides previous revision Previous revision Next revision | Previous revision | ||
component:component_access:zh [2023/11/29 08:18] hfsr [地址] |
component:component_access:zh [2023/12/27 04:26] (current) hfsr [地址] |
||
---|---|---|---|
Line 18: | Line 18: | ||
``` | ``` | ||
- | 注意,即使从计算机上拆下来,物品组件的地址通常也不会改变。因此,如果你移除一个硬盘再将其重新插入,它的地址仍与之前的相同。而方块组件则**不是**这样,拆除它们再重新安装后它们一定会得到一个新地址。 | + | 注意,即使从计算机上拆下来,物品组件的地址通常也不会改变。因此,如果你移除一个硬盘再将其重新插入,它的地址仍与之前的相同。而方块组件则**不是**这样,拆除它们再重新安装必然会改变地址。 |
你可以选择像这样过滤组件列表: | 你可以选择像这样过滤组件列表: | ||
Line 42: | Line 42: | ||
首选组件 | 首选组件 | ||
------ | ------ | ||
- | [[api:component:zh|component(组件) API]]会持续追踪每种组件类型的“首选”组件。如果同一种类型下有多个组件,则会随机选择一个作为首选组件。你可以通过 `component.xxx` 访问特定类型的首选组件,其中 `xxx` 是类型,比如: | + | [[api:component:zh|component(组件) API]]会持续追踪每种组件类型的“首选”组件。如果同一种类型下有多个组件,则会随机选择一个作为首选组件。你可以通过`component.xxx`访问特定类型的首选组件,其中`xxx`是类型,比如: |
```lua | ```lua | ||
lua> =component.gpu.address | lua> =component.gpu.address | ||
Line 48: | Line 48: | ||
``` | ``` | ||
- | 或者你也可以使用 `component.getPrimary("xxx")` 。切记,如果指定类型的首选组件不存在,调用此方法会抛出一个错误,因此最好先用 `component.isAvailable("xxx")` 进行检查。之所以选择直接抛出错误而不是返回 nil,是因为相较于在后续代码中试图访问 nil 中的元素而产生错误,直接在这里抛出一个错误更能明确问题来源。 | + | 或者你也可以使用`component.getPrimary("xxx")`。切记,如果指定类型的首选组件不存在,调用此方法会抛出一个错误,因此最好先用`component.isAvailable("xxx")`进行检查。之所以选择直接抛出错误而不是返回`nil`,是因为相较于在后续代码中试图访问`nil`中的元素而产生错误,直接在这里抛出一个错误更能明确问题来源。 |
这个系统主要是为了让操作系统选择初始输出屏幕。 | 这个系统主要是为了让操作系统选择初始输出屏幕。 | ||
Line 54: | Line 54: | ||
代理对象 | 代理对象 | ||
---- | ---- | ||
- | 现在我们知道了如何获得组件地址,现在让我们看看如何与它们互动。有两种方法可以做到这一点。一种是调用 `component.invoke(address, method, ...)` 。例如: | + | 现在我们已经知道了如何获得组件地址,那么看看如何与它们交互吧。有两种方法可以做到这一点。一种是调用`component.invoke(address, method, ...)`。例如: |
```lua | ```lua | ||
local component = require("component") | local component = require("component") | ||
Line 60: | Line 60: | ||
``` | ``` | ||
- | 通常而言,更好的方法是获取一个代理对象。代理对象是一个简单的表,为每个API回调提供一个以该回调命名的函数。此外,每个代理都有两个字段:`address` 用来保存被包装的组件的地址,`type` 用来保存组件的类型。你可以通过这种方法获得代理对象: | + | 通常而言,更好的方法是获取一个代理对象。代理对象是一个简单的表,为各个API回调提供同名的的函数。此外,每个代理都有两个字段:`address`,用来保存被包装的组件的地址。`type`,用来保存组件的类型。你可以通过这种方法获得代理对象: |
```lua | ```lua | ||
local component = require("component") | local component = require("component") | ||
local proxy = component.proxy(address) | local proxy = component.proxy(address) | ||
- | -- 下面的调用是通过代理对象进行的: | + | -- 上文调用的使用代理对象版本: |
proxy.broadcast(port, data) | proxy.broadcast(port, data) | ||
-- 常见的代理对象字段: | -- 常见的代理对象字段: | ||
- | print(proxy.address) -- 传给上述 component.proxy 的地址 | + | print(proxy.address) -- 传给上述component.proxy的地址 |
print(proxy.type) -- "modem" | print(proxy.type) -- "modem" | ||
``` | ``` | ||
- | 通过 `component.getPrimary` 或 `component.xxx` 访问的首选组件实际上都是代理对象。 | + | 请注意,通过`component.getPrimary`或`component.xxx`访问的首选组件实际上都是代理对象。 |
直接调用 | 直接调用 | ||
-------- | -------- | ||
- | 一些组件的回调可以以"直接调用"的形式执行。直接调用是在计算机的工作线程中进行的,这意味着它们会立即返回。普通调用会被委托给主服务端线程,以避免竞争条件和其他线程问题,这也意味着普通调用最多需要一个 tick(即50ms)。这里明确一下:只有component(组件) API 会有这种情况。 | + | 一些组件的回调可以以"直接调用"的形式执行。直接调用是在计算机的工作线程中进行的,这意味着它们会立即返回。普通调用会被委托给主服务端线程,以避免出现竞态问题或其他线程问题,这也意味着普通调用至多会需要一tick(即50ms)才能完成。这里明确一下:只有component(组件) API会有这种情况。 |
信号 | 信号 | ||
---- | ---- | ||
- | 与组件交互的一个重要部分是[[:component:signals:zh|信号]] 。信号可以被组件推入队列,以通知电脑外部变化和事件。例如,用户的输入就是通过信号转发给电脑的。电脑也可以将自己的信号加入队列,这有助于代码复用,或者只是异步通知你代码的其他部分。 | + | [[:component:signals:zh|信号]]是于组件交互时很重要的一部分。信号可以被组件推入队列,以通知电脑外部变化和事件。例如,用户的输入就是通过信号转发给电脑的。电脑也可以将自己的信号加入队列,这有助于代码复用,或者只是异步通知你代码的其他部分。 |
目录 | 目录 |