我已经阅读了教程中的"C绑定",但我是C的新手.
有人可以告诉我,如果一个Crystal程序可以构建为一个静态库来链接,如果可以的话,请你提供一个简单的例子吗?
根据我的理解,Nim中的字符串基本上是一个可变的字节序列,并且它们在赋值时被复制.
鉴于此,我认为这sizeof会告诉我(比如len)字节数,但它总是8在我的64位机器上给出,所以它似乎拿着一个指针.
鉴于此,我有以下问题......
复制作业背后的动机是什么?是因为它们是可变的吗?
有没有时间分配时不复制?(我假设非var功能参数不复制.还有别的吗?)
它们是否经过优化,只有当它们发生变异时才真正被复制?
字符串和序列之间是否有任何显着差异,或者上述问题的答案是否同样适用于所有序列?
还有什么其他值得注意的吗?
谢谢!
使用该import语句时,Nim如何/在何处执行模块搜索?
我知道可以使用文件路径,但是如果我不想使用文件路径,那么我将在本地定义的模块放在我的机器上?
我还没有使用过Nimble,我认为这是一种方式,但是我更感兴趣的是如果模块只在本地定义,它将如何完成.
是否将map其长度存储在某处或者是否在每次调用时进行计算len(my_map)?
语言规范为地图显示了这一点,这实际上没有帮助:
map元素的数量称为其长度.对于地图m,可以使用内置函数发现它,len并且可以在执行期间进行更改.可以在执行期间使用赋值添加元素,并使用索引表达式检索元素; 可以使用delete内置函数删除它们.
在"长度和容量"部分下,我们看到:
表达
len(s)如果是常数s是一个string常数.表达式len(s)和cap(s)常量,如果类型s是aarray或pointeraarray并且表达式s不包含channel接收或(非常量)函数调用; 在这种情况下s不评估.否则,调用len和cap不是常量并s进行评估.
所以它告诉我们这s不是常数并且被评估但是它没有说明它是否像对待slice类型一样被查找为存储值.
我正在尝试在Linux中将Nim中创建的一些代码静态链接到Go应用程序中.我已经关注了Nim Backend Integration文档和一些关于在Go中链接C但但没有得到它的文章.
这是我到目前为止的地方......
尼姆代码target.nim:
proc testnim* {.exportc.} =
echo "In Nim!"
Run Code Online (Sandbox Code Playgroud)
我编译它:
nim c --app:staticLib --noMain --header target.nim
Run Code Online (Sandbox Code Playgroud)
去代码app.go:
package main
/*
#cgo CFLAGS: -I/my/path/to/target/nimcache
#cgo CFLAGS: -I/my/path/to/Nim/lib
#cgo LDFLAGS: /my/path/to/target/libtarget.a
#include "/my/path/to/target/nimcache/target.h"
*/
import "C"
import "fmt"
func main() {
fmt.Println("In Go!")
C.NimMain()
C.testnim()
}
Run Code Online (Sandbox Code Playgroud)
我尝试构建它们:
go build
go build --ldflags '-extldflags "-static"' app.go
Run Code Online (Sandbox Code Playgroud)
这是我得到的:
# command-line-arguments /my/path/to/target/libtarget.a(stdlib_system.o): In function `nimUnloadLibrary': stdlib_system.c:(.text+0xe6f0): undefined reference to `dlclose' /my/path/to/target/libtarget.a(stdlib_system.o): In function `nimLoadLibrary': stdlib_system.c:(.text+0xe71b): undefined …
有可用的解析器在macros包中,如同parseExpr和parseStmt但他们是{.compileTime.}特效.
有没有办法在运行时解析一串Nim代码,产生一个可以分析的AST?
正如标题所述,我想知道检查迭代器是否完整的正确方法.
我在文档中找不到任何内容,但我在源代码中发现了类似的内容:
iter.next.is_a? Iterator::Stop
Run Code Online (Sandbox Code Playgroud)
玩具示例:
a = "a?c"
b = a.each_char
puts b.next # a
puts b.next # ?
puts b.next # c
puts b.next # #<Iterator::Stop:0x8ccbff8>
if b.next.is_a? Iterator::Stop
puts "DONE" # successfully prints DONE
end
Run Code Online (Sandbox Code Playgroud)
这是正确和正确的还是我应该使用不同的方式.
我的问题是,当调用方法时,_是否在接收者处创建了值的副本.
type Foo struct {
// Many fields, making a large struct
}
func (_ Foo) Test(v *T) int {
// Here we can't use the receiver but the method is still needed
}
Run Code Online (Sandbox Code Playgroud)
所以我想知道Go实现是否仍会Foo在Test()调用时复制值,即使实际上不可能改变接收器值.
var f Foo
f.Test() // Is this making a copy?
Run Code Online (Sandbox Code Playgroud)
我也想知道指针的情况,默认情况下会自动解除引用.
var f = new(Foo)
f.Test() // Is this making a copy?
Run Code Online (Sandbox Code Playgroud)
我试着看装配,我认为它可能正在制作副本,但我只是不知道足够确定.
有关情况的详细信息:
这是一个奇怪的情况,我不能使用指针.代码是机器生成的,并且需要在对v参数进行一些初始化时使类型满足接口.(生成的代码包含有关Foo设置的元数据v.)
因此,如果我将接收器设为指针,则"value"实例将不会满足接口.对于每个实例,此方法将被调用一次,并且实例有时可能很大和/或大量创建,这就是为什么我要避免不必要的副本.
如果我有一个其他文件需要的文件,是否可以获取需要它的文件的绝对文件路径?
因此,如果lib_file.cr有一个宏被意图由app_file.cr导入它调用,那宏可以app_file.cr在编译时发现文件路径吗?
我试过这样的东西:
macro tester
puts __DIR__
puts __FILE__
end
Run Code Online (Sandbox Code Playgroud)
但是当从执行需求的文件调用时,它在编译时没有提供任何内容,而这在运行时:
? expanded macro: app_file
如果我将宏更改为:
macro tester
{{puts __DIR__}}
{{puts __FILE__}}
end
Run Code Online (Sandbox Code Playgroud)
它在编译时给我这个:
"/home/user/Documents/crystal_test/lib_file" "/home/user/Documents/crystal_test/lib_file.cr"
那么有一个技巧可以在编译时获得app_file.cr内部的完整路径lib_file.cr吗?
我知道Crystal有一个用于在编译时定义代码的宏系统,但除此之外是否可以运行代码?
例如,我们可以这样做,以便它在编译期间运行吗?
puts "foobar"
Run Code Online (Sandbox Code Playgroud)
或者对于一个更严肃的例子,我们可以读取和写入运行编译器的文件系统吗?
我一直在OS X中使用Crystal,与Homebrew一起安装.现在我在Linux上尝试一下,但是当我编译一个包含URI标准库的项目时,我得到:
需要"URI"时:无法找到相对于'/ home/...'的文件'URI'
我根据文档使用安装apt-get.(如果重要的话,我实际上正在使用LinuxMint.)我是否还需要下载git repo?如果是这样,Crystal希望它在哪里?
我下载了一个预编译的二进制文件.我看到它包括标准库.Crystal寻找的是PATH吗?
crystal-lang ×5
nim-lang ×4
go ×3
compile-time ×1
dictionary ×1
import ×1
installation ×1
linux ×1
module ×1
string ×1