В этом случае я рекомендую игнорировать предупреждение о триггере, поскольку, похоже, оно работает нормально, несмотря на предупреждение. (Вывод триггера Дафни несколько чрезмерно консервативен, когда дело доходит до теоретических операторов множества, и Z3 может вывести хороший триггер на низком уровне.) Если вы действительно хотите это исправить, вот один из способов. Замените ветвь "then" вашего кода на
var s' := (s - {y});
var m := minimum(s');
out := (if y < m then y else m);
assert forall t :: t in s ==> t == y || t in s';
assert forall t : int :: t in s' ==> out <= t;
assert out <= y;
Вторая проблема (об эффективности) является несколько фундаментальной. (См. Статью Растана «Компиляция оператора Эпсилона Гильберта» , где упоминается, что компиляция операторов «дай-так-то» приводит к квадратичной производительности.) Я предпочитаю думать о set
Дафни как о математической конструкции, которая не должна быть скомпилированным. (Тот факт, что он может может быть скомпилирован, удобен для игрушечных программ, а не для реальных систем, где можно было бы ожидать реализации стандартных наборов библиотек, основанных на структуре данных.)