我尝试创建一个给定数字和列表的函数,将给定的数字添加到列表中并减少该数字。执行此操作直到数字达到0并返回列表。
IE" incList 5 []"应该返回[5,4,3,2,1]
这是我到目前为止的代码
incList :: Int -> [a] -> [a]
incList 0 xs = []
incList g [] = []
incList g (x:xs) = g:x ++ incList (g-1) (xs)
我正在使用' a'因为我希望列表以后包含任何内容。
我目前收到此错误:
Couldn't match expected type ‘[a]’ with actual type ‘a’
‘a’ is a rigid type variable bound by
the type signature for incList :: Int -> [a] -> [a]
at incList.hs:1:12
Relevant bindings include
xs :: [a] (bound at incList.hs:4:14)
x :: a (bound at incList.hs:4:12)
incList :: Int -> [a] -> [a] (bound at incList.hs:2:1)
In the first argument of ‘(++)’, namely ‘x’
In the second argument of ‘(:)’, namely ‘x ++ incList (g - 1) (xs)’
答案 0 :(得分:2)
据我所知,您希望预先挂起一个列表,其中包含从某个起始值开始倒数的数值。第一次尝试时会出现几种类型和逻辑错误:
incList :: Int -> [a] -> [a]
首先,您说您的起始值是Int
,但您的列表包含任何值(通过a
类型变量)。您不能拥有混合类型Int
和a
的列表,因此您必须以某种方式统一这些类型。
要明确的是,你说“我正在使用'a',因为我希望列表包含以后的任何内容。”但这不是一个有效的选项 - 列表必须只包含一种类型,而您似乎决定使用数字。
继续,我们开始使用自定义递归函数。制作你自己的很好,只要知道这可以通过内置函数或语法糖来处理。
incList 0 xs = []
incList g [] = []
你的第一个基础是好的,但是第二个基本情况,不是那么多。您明确说incList 5 []
不应该是[]
而是[5,4,3,2,1]
那么你如何放弃第二个案例。
incList g (x:xs) = g:x ++ incList (g-1) (xs)
在这里,你为什么要解构原始列表(x:xs
)。我认为你想要预先挂起值,而不是取消值并将新值与旧值混合。
此外,表达式g:x ++
毫无意义。 x
不是列表,因此g : x
也不是(++) :: Int -> Int -> Int
,因此它们没有为g : x : incList ...
提供有效参数,您可能会选择incList :: Int -> [Int] -> [Int]
incList 0 xs = xs
incList g xs = g : incList (g-1) xs
。
随着这些变化,我们到达:
incList g xs = [g,g-1..1] ++ xs
这几乎与:
相同<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:WpfApplication1.resoureces">
<SolidColorBrush x:Key="GlyphBrush" Color="#444" />
<Style x:Key="ExpandCollapseToggleStyle" TargetType="ToggleButton">
<Setter Property="Focusable" Value="False"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="ToggleButton">
<Grid Width="15" Height="13" Background="Transparent">
<Path x:Name="ExpandPath" HorizontalAlignment="Left" VerticalAlignment="Center" Margin="1,1,1,1" Fill="{StaticResource GlyphBrush}" Data="M 4 0 L 8 4 L 4 8 Z"/>
</Grid>
<ControlTemplate.Triggers>
<Trigger Property="IsChecked" Value="True">
<Setter Property="Data" TargetName="ExpandPath" Value="M 0 4 L 8 4 L 4 8 Z"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<Style x:Key="TreeViewItemFocusVisual">
<Setter Property="Control.Template">
<Setter.Value>
<ControlTemplate>
<Border>
<Rectangle Margin="0,0,0,0" StrokeThickness="5" Stroke="Black" StrokeDashArray="1 2" Opacity="0"/>
</Border>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<Style x:Key="{x:Type TreeViewItem}" TargetType="{x:Type TreeViewItem}">
<Setter Property="Background" Value="Transparent"/>
<Setter Property="HorizontalContentAlignment" Value="{Binding Path=HorizontalContentAlignment, RelativeSource={RelativeSource AncestorType={x:Type ItemsControl}}}"/>
<Setter Property="VerticalContentAlignment" Value="{Binding Path=VerticalContentAlignment, RelativeSource={RelativeSource AncestorType={x:Type ItemsControl}}}"/>
<Setter Property="Padding" Value="1,0,0,0"/>
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}"/>
<Setter Property="FocusVisualStyle" Value="{StaticResource TreeViewItemFocusVisual}"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type TreeViewItem}">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition MinWidth="19"
Width="Auto"/>
<ColumnDefinition Width="Auto"/>
<ColumnDefinition Width="*"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition/>
</Grid.RowDefinitions>
<ToggleButton x:Name="Expander" Style="{StaticResource ExpandCollapseToggleStyle}" IsChecked="{Binding Path=IsExpanded, RelativeSource={RelativeSource TemplatedParent}}" ClickMode="Press"/>
<Border Name="Bd" Grid.Column="1" Background="{TemplateBinding Background}" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}" Padding="{TemplateBinding Padding}">
<ContentPresenter x:Name="PART_Header" ContentSource="Header" HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"/>
</Border>
<ItemsPresenter x:Name="ItemsHost" Grid.Row="1" Grid.Column="1" Grid.ColumnSpan="2"/>
</Grid>
<ControlTemplate.Triggers>
<Trigger Property="IsExpanded" Value="false">
<Setter TargetName="ItemsHost" Property="Visibility" Value="Collapsed"/>
</Trigger>
<!--<Trigger Property="HasItems" Value="false">
<Setter TargetName="Expander" Property="Visibility" Value="Hidden"/>
</Trigger>-->
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="HasHeader" Value="false"/>
<Condition Property="Width" Value="Auto"/>
</MultiTrigger.Conditions>
<Setter TargetName="PART_Header" Property="MinWidth" Value="75"/>
</MultiTrigger>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="HasHeader" Value="false"/>
<Condition Property="Height" Value="Auto"/>
</MultiTrigger.Conditions>
<Setter TargetName="PART_Header" Property="MinHeight" Value="19"/>
</MultiTrigger>
<Trigger Property="IsSelected" Value="true">
<Setter TargetName="Bd" Property="Background" Value="{DynamicResource {x:Static SystemColors.HighlightBrushKey}}"/>
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.HighlightTextBrushKey}}"/>
</Trigger>
<MultiTrigger>
<MultiTrigger.Conditions>
<Condition Property="IsSelected" Value="true"/>
<Condition Property="IsSelectionActive" Value="false"/>
</MultiTrigger.Conditions>
<Setter TargetName="Bd" Property="Background" Value="{DynamicResource {x:Static SystemColors.ControlBrushKey}}"/>
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.ControlTextBrushKey}}"/>
</MultiTrigger>
<Trigger Property="IsEnabled" Value="false">
<Setter Property="Foreground" Value="{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</ResourceDictionary>
阅读起来有点清洁。
答案 1 :(得分:1)
++
运算符是列表并置运算符。它的类型是[a] -> [a] -> [a]
。这意味着它的输入都是列表。正如您从错误中看到的那样,您将x
作为++
的第一个输入,而x
的类型只是a
。
尝试将此++
替换为:
,例如:
incList g (x:xs) = g : x : incList (g-1) (xs)
:
的类型为a -> [a] -> [a]
,这应该适用于此处。可能还有其他问题,我没有检查过。