使用ghc编译Haskell代码时出现专门化警告 [英] Warning on specialisations when compiling Haskell Code with ghc

查看:174
本文介绍了使用ghc编译Haskell代码时出现专门化警告的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

$ ghc --make -O2 -Wall -fforce-recomp


[1 of 1]编译主(
isPrimeSmart.hs,isPrimeSmart.o)
SpecConstr
函数`$ wa {v s2we} [ ']
有两种调用模式,但限制为1
使用-fspec-constr-count = n来设置界限
使用-dppr-debug查看专业化链接isPrimeSmart

$ b $ /

我的代码是:

  { - #OPTIONS_GHC -O2 -optc -O2# - } 

导入合格的Data.ByteString.Lazy.Char8作为StrL - StrL是STRing库
导入数据.List

- 读入文件。第一行显示了多少个案例。每个案例都在一个单独的
- 线上,上边界由空格分隔。打印所有素数
- 在下限和上限之间。每个案例的结果分别为
- 一个空白行。
main :: IO()
main = do
let factors = takeWhile(< =(ceiling $ sqrt(1000000000 :: Double)))allPrimes
(l:ls )< - StrL.lines`fmap` StrL.getContents
let numCases = readInt l
let cases =(take numCases ls)
sequence_ $ intersperse(putStrLn)$ map(doLine因素)案例

- 获取并打印在一行上指定的整数之间的所有素数。
doLine :: [Integer] - > StrL.ByteString - > IO()
doLine因子l = mapM_ print $ primesForLine因子l


--------------------- - 此行下方的纯代码------------------------------

- 获取所有的素数一行中指定的整数。
primesForLine :: [Integer] - > StrL.ByteString - > [整数]
primesForLine因子l = getPrimes因子范围
其中
范围= rangeForLine l

- 生成要检查的数字列表,将其存储在列表中,然后检查它们...
getPrimes :: [Integer] - > (整数,整数) - > [整数]
getPrimes因子范围=过滤器(isPrime因子)(获取候选范围)

- 基于上限和下限生成候选值列表
getCandidates ::(Integer ,整数) - > [Integer]
getCandidates(propStart,propEnd)= list
其中
list = if propStart< 3
then 2:oddList
else oddList
oddList = [listStart,listStart + 2 .. propEnd]
listStart = if cleanStart`rem` 2 == 0
然后cleanStart + 1
else cleanStart
cleanStart = if propStart< 3
然后3
else propStart

- 一条线总是有一个空格分隔的下限和上限。
rangeForLine :: StrL.ByteString - > (整数,整数)
rangeForLine caseLine =开始`seq`结束`seq`(开始,结束)
其中
[开始,结束] =(地图readInteger $ StrL.words caseLine): :[Integer]


- 从ByteString读取整数
readInteger :: StrL.ByteString - >整数
readInteger x =
case Just(i,_) - >的StrL.readInteger x我
无 - >错误Unparsable Integer

- 从ByteString读取一个Int
readInt :: StrL.ByteString - >诠释
readInt x =
case Just(i,_) - >>的StrL.readInt x我
无 - >错误Unparsable Int

- 以懒惰的方式生成所有素数。
allPrimes :: [Integer]
allPrimes = ps(2:[3,5 ..])
其中
ps(np:candidates)= - np代表New总理
np:ps(过滤器(\ n - > n`rem` np / = 0)候选人)
ps [] =错误这不可能发生,但会关闭编译器

- 通过与这些因素进行比较来检查它是否是主要的。
isPrime :: [Integer] - >整数 - > Bool
isPrime因子val = all(\ f - > val`rem` f / = 0)validFactors
其中
validFactors = takeWhile(< ceil)因子
ceil =((ceiling)$ sqrt $((fromInteger val):: Double))):: Integer

我不知道如何解决这个警告。我如何开始?我是否编译汇编并匹配错误?这些警告甚至意味着什么?

解决方案

这些只是(恼人的)警告,表明GHC可以对代码进行进一步的专业化如果你真的想。未来版本的GHC可能不会默认发布这些数据,因为无论如何你无能为力。



它们是无害的,并不是错误。不要担心他们。




要直接解决问题,可以使用 -w (取消警告)而不是 -Wall



例如在文件 { - #OPTIONS_GHC -w# - } 将禁用警告。



或者,增加专门化阈值会使警告消失,例如 -fspec-constr-count = 16


I get the following error when trying to compile

$ ghc --make -O2 -Wall -fforce-recomp

[1 of 1] Compiling Main ( isPrimeSmart.hs, isPrimeSmart.o ) SpecConstr Function `$wa{v s2we} [lid]' has two call patterns, but the limit is 1 Use -fspec-constr-count=n to set the bound Use -dppr-debug to see specialisations Linking isPrimeSmart ...

My code is:

{-# OPTIONS_GHC -O2 -optc-O2 #-}

import qualified Data.ByteString.Lazy.Char8 as StrL -- StrL is STRing Library
import Data.List

-- read in a file. First line tells how many cases. Each case is on a separate 
-- line with the lower an upper bounds separated by a space. Print all primes
-- between the lower and upper bound. Separate results for each case with
-- a blank line.
main :: IO ()
main = do
   let factors = takeWhile (<= (ceiling $ sqrt (1000000000::Double))) allPrimes
   (l:ls) <- StrL.lines `fmap` StrL.getContents
   let numCases = readInt l
   let cases = (take numCases ls)
   sequence_ $ intersperse (putStrLn "") $ map (doLine factors) cases

-- get and print all primes between the integers specified on a line.
doLine :: [Integer] -> StrL.ByteString -> IO ()
doLine factors l = mapM_ print $ primesForLine factors l


---------------------- pure code below this line ------------------------------

-- get all primes between the integers specified on a line.
primesForLine :: [Integer] -> StrL.ByteString -> [Integer]
primesForLine factors l = getPrimes factors range  
  where
    range = rangeForLine l

-- Generate a list of numbers to check, store it in list, and then check them...
getPrimes :: [Integer] -> (Integer, Integer) -> [Integer]
getPrimes factors range  = filter (isPrime factors) (getCandidates range)

-- generate list of candidate values based on upper and lower bound
getCandidates :: (Integer, Integer) -> [Integer]
getCandidates (propStart, propEnd) = list
  where
    list = if propStart < 3
           then 2 : oddList
           else oddList
    oddList = [listStart, listStart + 2 .. propEnd]
    listStart = if cleanStart `rem` 2 == 0
                then cleanStart + 1
                else cleanStart
    cleanStart = if propStart < 3
                 then 3
                 else propStart

-- A line always has the lower and upper bound separated by a space. 
rangeForLine :: StrL.ByteString -> (Integer, Integer)
rangeForLine caseLine = start `seq` end `seq` (start, end)
  where
    [start, end] = (map readInteger $ StrL.words caseLine)::[Integer]


-- read an Integer from a ByteString
readInteger :: StrL.ByteString -> Integer
readInteger x =
  case StrL.readInteger x of Just (i,_) -> i
                             Nothing    -> error "Unparsable Integer"

-- read an Int from a ByteString
readInt :: StrL.ByteString -> Int
readInt x =
  case StrL.readInt x of Just (i,_) -> i
                         Nothing    -> error "Unparsable Int"

-- generates all primes in a lazy way.
allPrimes :: [Integer]
allPrimes = ps (2:[3,5 .. ])
  where
    ps (np:candidates) =  -- np stands for New Prime
        np : ps (filter (\n -> n `rem` np /= 0) candidates)
    ps [] = error "this can't happen but is shuts up the compiler"

-- Check to see if it is a prime by comparing against the factors.
isPrime :: [Integer] -> Integer -> Bool
isPrime factors val = all (\f -> val `rem` f /= 0) validFactors
  where
    validFactors = takeWhile (< ceil) factors
    ceil = ((ceiling $ sqrt $ ((fromInteger val)::Double))) :: Integer

I have no idea how to fix this warning. How do I start? Do I compile to assembly and match the error up? What does the warning even mean?

解决方案

These are just (annoying) warnings, indicating that GHC could do further specializations to your code if you really want to. Future versions of GHC will likely not emit this data by default, since there's nothing you can do about it anyway.

They are harmless, and are not errors. Don't worry about them.


To directly address the problem, you can use -w (suppress warnings) instead of -Wall.

E.g. in a file {-# OPTIONS_GHC -w #-} will disable warnings.

Alternately, increasing the specialization threshold will make the warning go away, e.g. -fspec-constr-count=16

这篇关于使用ghc编译Haskell代码时出现专门化警告的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆