Haskell 为什么GHCi了解GHC不了解的进口';T
我对哈斯克尔是个新手,我想我在某个地方有一个基本的误解。当我在GHCi中时(使用Haskell 为什么GHCi了解GHC不了解的进口';T,haskell,ghc,ghci,Haskell,Ghc,Ghci,我对哈斯克尔是个新手,我想我在某个地方有一个基本的误解。当我在GHCi中时(使用GHCi命令),我可以键入import System.Random,并且它可以工作。然后我可以生成随机数 接下来,我创建一个名为test.hs的文件,该文件只包含一行:importsystem.Random。然后调用命令ghc test.hs,得到以下错误消息: test.hs:1:1: error: Could not find module ‘System.Random’ There are fi
GHCi
命令),我可以键入import System.Random
,并且它可以工作。然后我可以生成随机数
接下来,我创建一个名为test.hs
的文件,该文件只包含一行:importsystem.Random
。然后调用命令ghc test.hs
,得到以下错误消息:
test.hs:1:1: error:
Could not find module ‘System.Random’
There are files missing in the ‘random-1.1’ package,
try running 'ghc-pkg check'.
Use -v to see a list of the files searched for.
|
1 | import System.Random
| ^^^^^^^^^^^^^^^^^^^^
但是,如果返回GHCi,我可以键入:load test.hs
。这是可行的,并允许我生成随机数
当我运行ghc pkg检查时,我只收到关于缺少haddock接口文件的警告:。据我所知,这与当前问题无关
另外,当我运行ghc pkg list
时,random-1.1
在列表中,因此应该安装random
有几个问题:
- 为什么GHC和GHCi可以获得不同的进口?为什么系统是这样设置的?也许我只是不理解GHC和GHCi之间的关系
- 根据错误消息,有“文件丢失”。我如何才能确定哪些文件
- 如何才能编译使用
的Haskell文件System.Random
编辑:GHC和GHCi都是同一版本
$ ghc --version
The Glorious Glasgow Haskell Compilation System, version 8.6.4
$ ghci --version
The Glorious Glasgow Haskell Compilation System, version 8.6.4
编辑:ghc和ghci都在/usr/bin/
$ which ghc
/usr/bin/ghc
$ which ghci
/usr/bin/ghci
更新:看起来这是一个ArchLinux特性,而不是一个损坏的包。我已经相应地更新了我的答案 GHCi加载模块的“动态”版本。默认情况下,GHC链接到模块的“静态”版本。特别是,当您运行时:
> import System.Random
在GHCi下,它尝试访问文件Random.dyn_hi
,以获取模块的接口信息。相反,当编译一个包含import语句的文件时,GHC会尝试访问该文件Random.hi
您可以通过运行ghc pkg field random import dirs
并查看结果目录来验证这一问题。应该有一个System
子目录,其中通常有两个文件:System.hi
和System.dyn\u hi
。如果前者不见了,那是你的问题
现在,看起来您可能正在使用ArchLinux。正如Arch中“链接问题”一节所述,Arch Haskell社区包(包括Haskell random
)有意省略接口文件和库的静态版本
这里给出了几种变通方法:
- 使用GHC编译时,可以使用动态链接。当直接使用GHC时,这只意味着传递
标志。对于基于Cabal的项目,该页面给出了修改-dynamic
以对所有项目使用动态链接的说明~/.Cabal/config
- 您可以安装
和ghc static
软件包,并在ghc pristine
中设置使用编译器的路径和/或阴谋,该编译器将维护自己的独立软件包数据库,不会干扰全局安装的Haskell社区软件包,像haskell random/usr/share/ghc pristine/bin/ghc
- 您可以安装
以获取基本库的静态版本,然后运行ghcstatic
cabalinstall--force重新安装所需的所有非基本包。请注意,Wiki注意到,这可能是乏味和复杂的,因为您必须手动确定所有包的依赖关系
ghc static
,或者在调用ghc时,您还可能会得到一个关于base
包中缺少文件的错误。您运行了cabal安装--force重新安装random
,但正如@dfeuer所指出的,运行以下命令可能更安全:
$ cabal install --force-reinstalls random-1.1
以确保重新安装了相同的版本
无论如何,它在用户特定的软件包目录中安装了一个额外的random
。如果您运行:
$ ghc-pkg list
$ ghc-pkg describe random
您将看到,random-1.1
列在全局数据库和用户数据库下:
/usr/lib/ghc-8.6.4/package.conf.d
...
random-1.1
...
/home/xxxx/.ghc/x86_64-linux-8.6.4/package.conf.d
random-1.1
如果你跑步:
$ ghc-pkg list
$ ghc-pkg describe random
您将看到它列出了两个单独安装的版本,这就是为什么现在使用ghc pkg field random import dirs
获得重复字段的原因
这不应该有什么问题。您的用户数据库将优先于全局数据库,因此在运行GHCi或GHC时将使用新安装的random
请注意,如果您改变主意并想退出此重新安装(或者尝试Wiki上建议的其他解决方案),您应该能够运行:
$ ghc-pkg unregister --user random
从技术上讲,这实际上不会删除包(因为编译后的版本仍然在
~/.cabal/lib
下),但它应该让事情回到原来的样子。它们是不同的版本吗?它们都是8.6.4版哪个ghc
和哪个ghci
显示了什么?我想您可能安装了两个haskell副本,其中一个已损坏。@amalloy两个都在/usr/bin/
中。我如何确定是否/在何处/如何安装了Haskell的两个副本?为了避免损坏,您可能需要指定已安装的包的相同版本。您的位置是Random.dyn\u hi
存在,但Random.hi
不存在。我运行了命令cabalinstall--force reinstall random
,现在我能够使用ghc
命令编译导入System.random
的文件。然而,现在当我运行ghc pkg field random import dirs
时,我有两行输出:import dirs:/home/finn/.cabal/lib/x86_64-linux-ghc-8.6.4/random-1.1-3ypV4EIycgb35PKjTYYr5q
和import dirs:/usr/lib/ghc-8.6.4/site-local/random-1。