如何将sexp_diff库适配为OUnit assert_equal的pp_diff参数
解决方案
方法一:适配sexp_diff为OUnit2的pp_diff函数
OUnit2的pp_diff参数需要一个接收格式化器和两个s-expression元组的函数。你可以基于sexp_diff库的diff结果,封装出符合要求的打印函数:
open OUnit2 open Sexplib.Sexp open Sexp_diff let sexp_pp_diff fmt (expected, actual) = (* 计算两个s-expression的差异 *) let diff_result = diff expected actual in (* 将差异输出到格式化器,假设sexp_diff提供了pp_diff用于打印diff结构 *) pp_diff fmt diff_result (* 使用示例 *) let test_parse_ast ctx = let actual_ast_sexp = parse_and_convert_to_sexp "input" in let expected_sexp = Sexp.of_string "(expected (ast structure))" in assert_equal ~cmp:Sexp.equal ~pp_diff:sexp_pp_diff expected_sexp actual_ast_sexp
如果sexp_diff没有现成的pp_diff打印函数,你可以自行将diff结构转为可读字符串后输出:
let sexp_pp_diff fmt (expected, actual) = let diff_result = Sexp_diff.diff expected actual in let diff_str = Format.asprintf "%a" Sexp_diff.pp diff_result in Format.pp_print_string fmt diff_str
方法二:序列化差异为断言失败消息
如果不想适配pp_diff,可以自定义断言函数,仅当比较失败时计算差异并作为错误消息抛出,避免无意义的diff计算:
open OUnit2 open Sexplib.Sexp open Sexp_diff let assert_sexp_equal expected actual = if Sexp.equal expected actual then () else let diff = diff expected actual in let diff_msg = Format.asprintf "Expected:\n%a\nActual:\n%a\nDifferences:\n%a" Sexp.pp expected Sexp.pp actual pp_diff diff in assert_failure diff_msg (* 使用示例 *) let test_parse_ast ctx = let actual_ast_sexp = parse_and_convert_to_sexp "input" in let expected_sexp = Sexp.of_string "(expected (ast structure))" in assert_sexp_equal expected_sexp actual_ast_sexp
这种方式会在断言失败时同时展示预期值、实际值和差异点,便于快速定位问题。
内容的提问来源于stack exchange,提问作者user2852699
相关产品推荐
相关产品推荐

