haskell - 尝试使用 if 跟踪函数
问题描述
expmod :: Integer -> Integer -> Integer -> Integer
expmod a n m | trace (show (a n m)) False = undefined
expmod a 0 m = 1
expmod a n m = let (q,r) = divMod n 2
ans = expmod a q m
if r == 0 then let ans = ans*ans `mod` m
in trace ("-->" ++ show ans) ans
else let ans = ans*ans*a `mod` m
in trace ("-->" ++ show ans) ans
我不确定为什么它在 if 语句中失败
error: parse error on input `if'
|
37 | if (r == 0) then let ans = ans*ans `mod` m
| ^^
如何跟踪具有 if 语句的函数?
解决方案
眼前的问题
要回答您的直接问题,您需要in
使用您的let
(下面代码中第三行的开头):
expmod a n m = let (q,r) = divMod n 2
ans = expmod a q m
in if r == 0 then let ans = ans*ans `mod` m
in trace ("-->" ++ show ans) ans
else let ans = ans*ans*a `mod` m
in trace ("-->" ++ show ans) ans
其他提示
当您使用 时let ans =
,您正在定义ans
,因此ans
等号右侧的任何内容都将引用等号ans
左侧的 ,而不是任何ans
其他地方定义的内容。因此,这将失败:
let ans = ans*ans `mod` m
就像是凭空说的一样let x = x*x `mod` m
。它只会给出无限递归,所以对两个ans
es 使用两个不同的变量名。
第三,更简单的方法是使用traceShowId :: Show a => a -> a
,它跟踪具有Show
实例的值。traceShowId x
计算结果为x
,因此您可以在想要使用的地方使用它x
。它也有痕迹x
。例如:
expmod a n m = let (q,r) = divMod n 2
ans = expmod a q m
in traceShowId $ if r == 0 then ans*ans `mod` m
else ans*ans*a `mod` m
这样打字就少多了。trace "vvv" . traceShowId $
如果箭头很重要,您也可以使用。
推荐阅读
- macos - Mac OS Nativescript Sidekick UI 闪烁
- xml - 如何添加 settings.xml 以将 Jenkins 的构建过程添加到 docker 映像
- python - 尝试通过步骤对字符串中的元素求和
- python - Python:对其中包含 n 个字典的字典进行排序的有效方法
- swift - 快速捏合缩放
- delphi - Delphi 的 Dropbox API,如何将数据发送回我的 Windows 应用程序?
- javascript - 无法在 d3 散点图的 x 轴上显示日期
- python - 在具有混合 int 和字符串 python 的数据帧上使用 groupby.sum()
- java - 从 android 应用程序执行外部程序
- python - XGBRegressor.fit() 失败并显示“没有可用于执行的内核映像”