在Erlang shell中,如何自动读取所有记录定义标头

发布于 2024-09-30 00:31:04 字数 295 浏览 3 评论 0原文

这始于一个问题:

几乎每次我使用 Erlang shell 时,我都想在 shell 启动时运行一些命令,例如类似

rr("*.hrl").

或类似的命令。目前,每次启动 Erlang shell 时我都必须输入它,我已经厌倦了它并且总是忘记它。

但是这实际上是一个错误的问题!因为我真正想做的是在每个 shell 作业中读取我的记录定义标头。不用于在启动时运行的其他 shell 内置命令。因此,我更改了问题标题以显示应该如何提出的问题。

This started off as the question:

Almost every time when I use the Erlang shell, I'd like to run some command on shell startup, e.g. something like

rr("*.hrl").

Or similar. Currently I have to type it every time I start a Erlang shell and I'm getting tired of it and forget it all the time.

But this was actually the wrong question! For what I actually wanted to do is read my record definition headers in every shell job. Not use for other of the shell built-in commands to run on startup. So I changed the question header to show the question how it should have asked.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

厌倦 2024-10-07 00:31:04

在尝试使用 .erlang 解决方案时,我偶然发现了针对特定 rr/1 用法的解决方案:

来自 shell 的手册页:

在 shell 中对读取和打印记录有一些支持。
在编译期间,记录表达式被转换为元组表达式
西翁。在运行时,不知道元组是否实际上代表一个
记录。编译器使用的记录定义也无法在
运行时。因此,为了读取记录语法并将元组打印为
如果可能的话,记录定义必须由
外壳本身。用于读取、定义、遗忘的 shell 命令
列表和打印记录描述如下。注意每项工作
有自己的一组记录定义。方便记录事项
模块 shell_default 和 user_default 中的定义(如果已加载)
每次开始新作业时都会读取。例如,添加行

 -include_lib("kernel/include/file.hrl")。

to user_default 使得 file_info 的定义很容易在
外壳。

为了澄清起见,我添加了一些示例:

File foo.hrl:

-record(foo, {bar, baz=5}).

File: user_default.erl:

-module(user_default).
-compile(export_all).

-include("foo.hrl").  % include all relevant record definition headers here

 %% more stuff probably ...

Lets try out in the shell:

$ erl
Erlang R13B04 (erts-5.7.5) [source] [smp:2:2] [rq:2] [async-threads:0] [hipe] [kernel-poll:false]

Eshell V5.7.5  (abort with ^G)
1> #foo{}.
#foo{bar = undefined,baz = 5}

→ shell 了解来自 的记录foo.hrl

While trying the solution with .erlang I stumbled upon a solution for the specific rr/1 usage:

From the man-page of shell:

There is some support for reading and printing records in the shell.
During compilation record expressions are translated to tuple expres-
sions. In runtime it is not known whether a tuple actually represents a
record. Nor are the record definitions used by compiler available at
runtime. So in order to read the record syntax and print tuples as
records when possible, record definitions have to be maintained by the
shell itself. The shell commands for reading, defining, forgetting,
listing, and printing records are described below. Note that each job
has its own set of record definitions. To facilitate matters record
definitions in the modules shell_default and user_default (if loaded)
are read each time a new job is started. For instance, adding the line

  -include_lib("kernel/include/file.hrl").

to user_default makes the definition of file_info readily available in
the shell.

For clarification I add some example:

File foo.hrl:

-record(foo, {bar, baz=5}).

File: user_default.erl:

-module(user_default).
-compile(export_all).

-include("foo.hrl").  % include all relevant record definition headers here

 %% more stuff probably ...

Lets try out in the shell:

$ erl
Erlang R13B04 (erts-5.7.5) [source] [smp:2:2] [rq:2] [async-threads:0] [hipe] [kernel-poll:false]

Eshell V5.7.5  (abort with ^G)
1> #foo{}.
#foo{bar = undefined,baz = 5}

→ the shell knows about the record from foo.hrl

云之铃。 2024-10-07 00:31:04

文件 .erlang 在 shell 启动时进行计算,但它不在 shell 上下文中进行计算。这意味着它只能包含要计算的一般表达式,而不能包含 shell 命令。不幸的是, rr() 是一个 shell 命令(它初始化本地 shell 数据以识别记录),因此它不能在 .erlang 文件中使用。

虽然必须预加载的用户定义模块 user_default 可以使用 -include-include_lib 包含包含记录定义的文件,但这些记录定义然后将仅可用于 user_default 中定义的函数。 user_default 是普通的编译模块,其中的导出函数像任何其他函数一样被调用,因此记录定义在 shell 中不可见。 user_default 允许用户定义更复杂的函数,这些函数可以作为 shell 命令从 shell 中调用。

编辑:

我在这里部分错了。虽然我对 .erlang 的计算方式以及 user_default 中的函数的调用方式是正确的,但我错过了在 shell 启动时如何扫描 user_default.erl用于记录定义,然后在 shell 中可用。感谢@Peer Stritzinger 指出了这一点。

The file .erlang is evaluated when the shell is started, but it is NOT evaluated in the context of the shell. This means that it can only contain general expressions which are evaluated and not shell commands. Unfortunately rr() is a shell command (it initialises local shell data to recognise records) so it can not be used in the .erlang file.

While the user defined module user_default, which must be preloaded, can include files which contain record definitions using -include or -include_lib, these record definitions will then only be available to functions defined within user_default. user_default is normal compiled module and exported functions in it are called as any other functions so the record definitions will not be visible within the shell. user_default allows the user to define more complex functions which can be called from within the shell as shell commands.

EDIT:

I was partially wrong here. While I was correct about how .erlang is evaluated and how the functions in user_default are called I missed how user_default.erl is scanned at shell startup for record definitions which are then available within the shell. Thanks @Peer Stritzinger for pointing this out.

向日葵 2024-10-07 00:31:04

将其放在主目录中名为 .erlang 的文件中(请参阅 http://www.erlang.org/documentation/doc-5.2/doc/getting_started/getting_started.html)。

Place it in file called .erlang in your home directory (see paragraph 1.7.1 in http://www.erlang.org/documentation/doc-5.2/doc/getting_started/getting_started.html).

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文