简体   繁体   English

具有不同类型的Haskell类型签名

[英]Haskell type signatures with different types

I'm trying to create a function that takes a list of items and returns a list of either A) tuples of the form (2, "X") if the item "X" appears twice consecutively, or B) the item itself if it is not adjacent to a duplicate. 我正在尝试创建一个接受项列表并返回以下列表的函数:A)如果项“ X”连续出现两次,则形式为(2,“ X”)的元组,或者返回B)项本身。它不与重复项相邻。

Example: 例:

encode ["A", "A", "A", "B", "C", "C", "B", "B", "B", "D"]
> [(3, "A"), "B", (2, "C"), (3, "B"), "D"]

What would the appropriate type signature be? 适当的类型签名是什么? I have tried this: 我已经试过了:

data listItem a = (Integer, a) | a
encode :: (Eq a) => [a] -> [listItem a]

But I get this error: 但是我得到这个错误:

parse error in constructor in data/newtype declaration: (Integer, a) 

I peeked at the solution to this problem, which gave me this type signature: 我偷看了这个问题的解决方案,这给了我这种类型签名:

data ListItem a = Single a | Multiple Int a
    deriving (Show)
encode :: Eq a => [a] -> [ListItem a]

But when using this simple test 但是当使用这个简单的测试时

encode [x] = [x]

I get an error: 我收到一个错误:

Could not deduce (a ~ ListItem a)
from the context (Eq a)
  bound by the type signature for
             encode :: Eq a => [a] -> [ListItem a]
  at 99problems.hs:117:19-45
  `a' is a rigid type variable bound by
      the type signature for
        encode :: Eq a => [a] -> [ListItem a]
      at 99problems.hs:117:19
In the expression: x
In the expression: [x]

What is the right type signature for this problem? 此问题的正确类型签名是什么?

The "99 Problems" set was, as I understand it, written for Prolog originally, and then translated to Lisp. 据我了解,“ 99个问题”集最初是为Prolog编写的,然后翻译为Lisp。 It was then ... ah ... transliterated to Haskell. 那时……啊……音译成Haskell。 Unfortunately, things that make sense in Lisp don't always make so much sense in Haskell, so taking the problem descriptions too literally will get you into trouble. 不幸的是,在Lisp中有意义的事情在Haskell中并不总是那么有意义,因此,从字面上看问题描述会给您带来麻烦。 What the hint is telling you is that instead of trying to write a function producing a list like [(3, "A"), "B", (2, "C"), (3, "B"), "D"] , which is simply impossible in Haskell, you should aim to produce a list looking like [Multiple 3 "A", Single "B", Multiple 2 "C", Multiple 3 "B", Single "D"] . 提示告诉您的是,与其尝试编写一个产生像[(3, "A"), "B", (2, "C"), (3, "B"), "D"] ,这在Haskell中根本是不可能的,您应该以生成类似[Multiple 3 "A", Single "B", Multiple 2 "C", Multiple 3 "B", Single "D"]

The suggested type signature is correct; 建议的类型签名正确; you just need to write code to match it. 您只需要编写与之匹配的代码即可。

Note 注意

As I said, the 99 Problems set does not tend to be very Haskellian. 就像我说的那样,“ 99个问题集”并不是很像Haskellian。 It does not respect the usual idiomatic style of Haskell code at all , so you should not take it as a model for how to write Haskell code. 它不尊重的Haskell代码通常惯用的风格可言 ,所以你应该把它作为如何编写Haskell代码的典范。 For example, a Haskell programmer (or, for that matter, a sane Lisp programmer) probably would just produce a list of (Int,a) pairs, and not bother with that single/multiple nonsense that makes everything more complicated, less uniform, and very likely slower in a real application. 例如,Haskell程序员(或者,理智的Lisp程序员)可能只会生成(Int,a)对的列表,而不会打扰那种使所有事情变得更加复杂,不那么统一的废话。并且在实际应用中很可能会变慢。

A couple other ways "99 Problems" tends to break the usual expectations of Haskell programming: “ 99问题”的其他几种方式往往会破坏Haskell编程的通常期望:

  1. It tends to put arguments in a different order than a Haskell programmer would. 它倾向于将参数置于与Haskell程序员不同的顺序。 If a function takes a list and a number, a Haskell programmer will almost always put the number first and the list second; 如果一个函数接受一个列表和一个数字,Haskell程序员几乎总是将数字放在第一位,列表放在第二位; "99 Problems" tends to do it the other way around. “ 99问题”趋向于相反。

  2. Haskell programmers almost always use 0-based indexing for lists, arrays, etc. "99 Problems" seems to like 1-based indexing. Haskell程序员几乎总是对列表,数组等使用基于0的索引。“ 99问题”似乎喜欢基于1的索引。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM