我如何获得连续二进制数字串?

时间:2014-02-26 22:06:18

标签: haskell

如何输入iterate这样的功能:showIntAtBase a intToDigit b ""?我尝试使用合成(showIntAtBase a intToDigit (\x -> iterate (+1) 0) ""),但这绝对不正确。

例如,我正在尝试从无限列表中的十进制数生成二进制数字串: take 7 $ myFunc => ["0", "01", "10", "11", "100", "101", "110"]

2 个答案:

答案 0 :(得分:2)

因此,根据您的示例,您需要执行以下步骤:

  1. n = "0"
  2. 开始
  3. n转换为Int
  4. 1添加到nInt
  5. nInt转换为基础2 String
  6. 转到第2步。
  7. 这确实是iterate函数的一个很好的应用程序;但是看起来你的功能构成和命令都搞砸了。我将假设你定义了以下功能:

    -- Converts `n` to base `base` as a String
    showIntAtBase :: Int -> Int -> String
    showIntAtBase base n = undefined
    
    -- Converts the String `s` to an `Int` assuming its in base `base`
    readIntBase :: Int -> String -> Int
    readIntBase base s = undefined
    

    这样

    showIntAtBase b . readIntBase b === id
    -- and
    readIntBase b . showIntAtBase b === id
    

    由您来证明这些功能是相互反转并且正常工作。

    然后我会编写一个为我执行第2步到第4步的函数

    incrBase2 :: String -> String
    incrBase2 s = showIntAtBase 2 $ (\x -> x + 1) $ readIntBase 2 s
    

    或者,您可以更简单地将其写为

    incrBase2 = showIntAtBase 2 . (+1) . readIntBase 2
    

    现在,您可以在iterate上使用incrBase2

    allBinary :: [String]
    allBinary = iterate incrBase2 "0"
    

答案 1 :(得分:1)

"0"除外,所有数字均以1开头。因此,我们只考虑以1开头的二进制数尾部发生的情况:

""    -- 1
"0"   -- 10
"1"   -- 11
"00"  -- 100
"01"  -- 101
"10"  -- 110
"11"  -- 111

我们在这里看到的是一种模式,首先我们将0附加到前一次迭代结果的头部,然后我们以相同的方式追加1

ts = concat $ iterate (\xss -> [h:xs | h <-['0','1'], xs <- xss]) [[]]

产生那些尾巴。

只需在列表的开头添加"0",然后将1添加到尾部列表中:

bins = "0" : map ('1':) ts where
   ts = concat $ iterate (liftM2 (:) "01"]) [[]]