We consider the system plode. Alphabet: cons : [nat * list] --> list explode : [list * nat -> nat * nat] --> nat implode : [list * nat -> nat * nat] --> nat nil : [] --> list op : [nat -> nat * nat -> nat] --> nat -> nat Rules: op(f, g) x => f (g x) implode(nil, f, x) => x implode(cons(x, y), f, z) => implode(y, f, f z) explode(nil, f, x) => x explode(cons(x, y), f, z) => explode(y, op(f, f), f z) This AFS is converted to an AFSM simply by replacing all free variables by meta-variables (with arity 0). We use rule removal, following [Kop12, Theorem 2.23]. This gives the following requirements (possibly using Theorems 2.25 and 2.26 in [Kop12]): op(F, G) X >? F (G X) implode(nil, F, X) >? X implode(cons(X, Y), F, Z) >? implode(Y, F, F Z) explode(nil, F, X) >? X explode(cons(X, Y), F, Z) >? explode(Y, op(F, F), F Z) We use a recursive path ordering as defined in [Kop12, Chapter 5]. Argument functions: [[explode(x_1, x_2, x_3)]] = explode(x_1, x_3, x_2) [[implode(x_1, x_2, x_3)]] = implode(x_1, x_3, x_2) We choose Lex = {cons, explode, implode} and Mul = {@_{o -> o}, nil, op}, and the following precedence: cons = explode > implode > nil > op > @_{o -> o} Taking the argument function into account, and fixing the greater / greater equal choices, the constraints can be denoted as follows: @_{o -> o}(op(F, G), X) >= @_{o -> o}(F, @_{o -> o}(G, X)) implode(nil, F, X) >= X implode(cons(X, Y), F, Z) >= implode(Y, F, @_{o -> o}(F, Z)) explode(nil, F, X) > X explode(cons(X, Y), F, Z) > explode(Y, op(F, F), @_{o -> o}(F, Z)) With these choices, we have: 1] @_{o -> o}(op(F, G), X) >= @_{o -> o}(F, @_{o -> o}(G, X)) because [2], by (Star) 2] @_{o -> o}*(op(F, G), X) >= @_{o -> o}(F, @_{o -> o}(G, X)) because [3], by (Select) 3] op(F, G) @_{o -> o}*(op(F, G), X) >= @_{o -> o}(F, @_{o -> o}(G, X)) because [4] 4] op*(F, G, @_{o -> o}*(op(F, G), X)) >= @_{o -> o}(F, @_{o -> o}(G, X)) because op > @_{o -> o}, [5] and [7], by (Copy) 5] op*(F, G, @_{o -> o}*(op(F, G), X)) >= F because [6], by (Select) 6] F >= F by (Meta) 7] op*(F, G, @_{o -> o}*(op(F, G), X)) >= @_{o -> o}(G, X) because op > @_{o -> o}, [8] and [10], by (Copy) 8] op*(F, G, @_{o -> o}*(op(F, G), X)) >= G because [9], by (Select) 9] G >= G by (Meta) 10] op*(F, G, @_{o -> o}*(op(F, G), X)) >= X because [11], by (Select) 11] @_{o -> o}*(op(F, G), X) >= X because [12], by (Select) 12] X >= X by (Meta) 13] implode(nil, F, X) >= X because [14], by (Star) 14] implode*(nil, F, X) >= X because [15], by (Select) 15] X >= X by (Meta) 16] implode(cons(X, Y), F, Z) >= implode(Y, F, @_{o -> o}(F, Z)) because [17], by (Star) 17] implode*(cons(X, Y), F, Z) >= implode(Y, F, @_{o -> o}(F, Z)) because [18], [21], [23], [25] and [28], by (Stat) 18] cons(X, Y) > Y because [19], by definition 19] cons*(X, Y) >= Y because [20], by (Select) 20] Y >= Y by (Meta) 21] implode*(cons(X, Y), F, Z) >= Y because [22], by (Select) 22] cons(X, Y) >= Y because [19], by (Star) 23] implode*(cons(X, Y), F, Z) >= F because [24], by (Select) 24] F >= F by (Meta) 25] implode*(cons(X, Y), F, Z) >= @_{o -> o}(F, Z) because implode > @_{o -> o}, [23] and [26], by (Copy) 26] implode*(cons(X, Y), F, Z) >= Z because [27], by (Select) 27] Z >= Z by (Meta) 28] F >= F by (Meta) 29] explode(nil, F, X) > X because [30], by definition 30] explode*(nil, F, X) >= X because [31], by (Select) 31] X >= X by (Meta) 32] explode(cons(X, Y), F, Z) > explode(Y, op(F, F), @_{o -> o}(F, Z)) because [33], by definition 33] explode*(cons(X, Y), F, Z) >= explode(Y, op(F, F), @_{o -> o}(F, Z)) because [34], [37], [39] and [42], by (Stat) 34] cons(X, Y) > Y because [35], by definition 35] cons*(X, Y) >= Y because [36], by (Select) 36] Y >= Y by (Meta) 37] explode*(cons(X, Y), F, Z) >= Y because [38], by (Select) 38] cons(X, Y) >= Y because [35], by (Star) 39] explode*(cons(X, Y), F, Z) >= op(F, F) because explode > op, [40] and [40], by (Copy) 40] explode*(cons(X, Y), F, Z) >= F because [41], by (Select) 41] F >= F by (Meta) 42] explode*(cons(X, Y), F, Z) >= @_{o -> o}(F, Z) because explode > @_{o -> o}, [40] and [43], by (Copy) 43] explode*(cons(X, Y), F, Z) >= Z because [44], by (Select) 44] Z >= Z by (Meta) We can thus remove the following rules: explode(nil, F, X) => X explode(cons(X, Y), F, Z) => explode(Y, op(F, F), F Z) We use rule removal, following [Kop12, Theorem 2.23]. This gives the following requirements (possibly using Theorems 2.25 and 2.26 in [Kop12]): op(F, G, X) >? F (G X) implode(nil, F, X) >? X implode(cons(X, Y), F, Z) >? implode(Y, F, F Z) We use a recursive path ordering as defined in [Kop12, Chapter 5]. Argument functions: [[implode(x_1, x_2, x_3)]] = implode(x_2, x_1, x_3) We choose Lex = {cons, implode} and Mul = {@_{o -> o}, nil, op}, and the following precedence: cons = implode > nil > op > @_{o -> o} Taking the argument function into account, and fixing the greater / greater equal choices, the constraints can be denoted as follows: op(F, G, X) > @_{o -> o}(F, @_{o -> o}(G, X)) implode(nil, F, X) > X implode(cons(X, Y), F, Z) > implode(Y, F, @_{o -> o}(F, Z)) With these choices, we have: 1] op(F, G, X) > @_{o -> o}(F, @_{o -> o}(G, X)) because [2], by definition 2] op*(F, G, X) >= @_{o -> o}(F, @_{o -> o}(G, X)) because op > @_{o -> o}, [3] and [5], by (Copy) 3] op*(F, G, X) >= F because [4], by (Select) 4] F >= F by (Meta) 5] op*(F, G, X) >= @_{o -> o}(G, X) because op > @_{o -> o}, [6] and [8], by (Copy) 6] op*(F, G, X) >= G because [7], by (Select) 7] G >= G by (Meta) 8] op*(F, G, X) >= X because [9], by (Select) 9] X >= X by (Meta) 10] implode(nil, F, X) > X because [11], by definition 11] implode*(nil, F, X) >= X because [12], by (Select) 12] X >= X by (Meta) 13] implode(cons(X, Y), F, Z) > implode(Y, F, @_{o -> o}(F, Z)) because [14], by definition 14] implode*(cons(X, Y), F, Z) >= implode(Y, F, @_{o -> o}(F, Z)) because [15], [18], [19], [21], [22] and [18], by (Stat) 15] cons(X, Y) > Y because [16], by definition 16] cons*(X, Y) >= Y because [17], by (Select) 17] Y >= Y by (Meta) 18] F >= F by (Meta) 19] implode*(cons(X, Y), F, Z) >= Y because [20], by (Select) 20] cons(X, Y) >= Y because [16], by (Star) 21] implode*(cons(X, Y), F, Z) >= F because [18], by (Select) 22] implode*(cons(X, Y), F, Z) >= @_{o -> o}(F, Z) because implode > @_{o -> o}, [21] and [23], by (Copy) 23] implode*(cons(X, Y), F, Z) >= Z because [24], by (Select) 24] Z >= Z by (Meta) We can thus remove the following rules: op(F, G, X) => F (G X) implode(nil, F, X) => X implode(cons(X, Y), F, Z) => implode(Y, F, F Z) All rules were succesfully removed. Thus, termination of the original system has been reduced to termination of the beta-rule, which is well-known to hold. +++ Citations +++ [Kop12] C. Kop. Higher Order Termination. PhD Thesis, 2012.