Ответ 1
Мне кажется, что вы путаете понятия типов и конструкторов, это общая проблема, поскольку они живут в отдельных пространствах имен и часто получают одно и то же имя. В выражении Haskell
data SomeType = SomeType Int
скажем, вы фактически определяете тип SomeType
и конструктор SomeType
. Тип не является функцией в обычном смысле, но конструктор. Если вы спросите ghci о типе SomeType, вы получите следующее:
:t SomeType
SomeType :: Int -> SomeType
Теперь объявление type
является просто сокращением для более длинного определения типа, в вашем случае делая StackInt
синонимом Stack' Int
. Но для построения значения этого типа вам все равно нужно использовать конструктор Stack'
(который имеет тип [v] -> Int -> Stack' v
). Таким образом, ваш код должен быть
data Stack' v = Stack' [v] Int deriving (Show)
main = print(Stack' [1,2,3] 4)
Если вы хотите убедиться, что тип был Stack' Int
, вы можете добавить функцию
data Stack' v = Stack' [v] Int deriving (Show)
stackInt :: [Int] -> Int -> Stack' Int
stackInt list i = Stack' list i
main = print(stackInt [1,2,3] 4)
EDIT: Я также не написал stackInt list i = Stack' list i
для прозрачности здесь, но вы можете написать его более элегантно, как stackInt = Stack'
. Это ограничение типа, которое гарантирует, что вы получите правильный тип здесь.
Вы могли бы также иметь как новую функцию, так и синоним типа, если хотите, т.е.
data Stack' v = Stack' [v] Int deriving (Show)
type StackInt = Stack' Int
stackInt :: [Int] -> Int -> StackInt
stackInt list i = Stack' list i
main = print(stackInt [1,2,3] 4)