We consider the system h61. Alphabet: app : [] --> list -> list -> list cons : [] --> nat -> list -> list foldl : [] --> (list -> nat -> list) -> list -> list -> list iconsc : [] --> list -> nat -> list nil : [] --> list reverse : [] --> list -> list reverse1 : [] --> list -> list Rules: app nil x => x app (cons x y) z => cons x (app y z) foldl (/\x./\y.f x y) z nil => z foldl (/\x./\y.f x y) z (cons u v) => foldl (/\w./\x'.f w x') (f z u) v iconsc x y => cons y x reverse x => foldl (/\y./\z.iconsc y z) nil x reverse1 x => foldl (/\y./\z.app (cons z nil) y) nil x Using the transformations described in [Kop11], this system can be brought in a form without leading free variables in the left-hand side, and where the left-hand side of a variable is always a functional term or application headed by a functional term. We now transform the resulting AFS into an AFSM by replacing all free variables by meta-variables (with arity 0). This leads to the following AFSM: Alphabet: app : [list * list] --> list cons : [nat * list] --> list foldl : [list -> nat -> list * list * list] --> list iconsc : [list * nat] --> list nil : [] --> list reverse : [list] --> list reverse1 : [list] --> list ~AP1 : [list -> nat -> list * list] --> nat -> list Rules: app(nil, X) => X app(cons(X, Y), Z) => cons(X, app(Y, Z)) foldl(/\x./\y.~AP1(F, x) y, X, nil) => X foldl(/\x./\y.~AP1(F, x) y, X, cons(Y, Z)) => foldl(/\z./\u.~AP1(F, z) u, ~AP1(F, X) Y, Z) iconsc(X, Y) => cons(Y, X) reverse(X) => foldl(/\x./\y.iconsc(x, y), nil, X) reverse1(X) => foldl(/\x./\y.app(cons(y, nil), x), nil, X) foldl(/\x./\y.iconsc(x, y), X, nil) => X foldl(/\x./\y.iconsc(x, y), X, cons(Y, Z)) => foldl(/\z./\u.iconsc(z, u), iconsc(X, Y), Z) ~AP1(F, X) => F X Symbol ~AP1 is an encoding for application that is only used in innocuous ways. We can simplify the program (without losing non-termination) by removing it. Additionally, we can remove some (now-)redundant rules. This gives: Alphabet: app : [list * list] --> list cons : [nat * list] --> list foldl : [list -> nat -> list * list * list] --> list iconsc : [list * nat] --> list nil : [] --> list reverse : [list] --> list reverse1 : [list] --> list Rules: app(nil, X) => X app(cons(X, Y), Z) => cons(X, app(Y, Z)) foldl(/\x./\y.X(x, y), Y, nil) => Y foldl(/\x./\y.X(x, y), Y, cons(Z, U)) => foldl(/\z./\u.X(z, u), X(Y, Z), U) iconsc(X, Y) => cons(Y, X) reverse(X) => foldl(/\x./\y.iconsc(x, y), nil, X) reverse1(X) => foldl(/\x./\y.app(cons(y, nil), x), nil, X) We observe that the rules contain a first-order subset: app(nil, X) => X app(cons(X, Y), Z) => cons(X, app(Y, Z)) iconsc(X, Y) => cons(Y, X) Moreover, the system is orthogonal. Thus, by [Kop12, Thm. 7.55], we may omit all first-order dependency pairs from the dependency pair problem (DP(R), R) if this first-order part is terminating when seen as a many-sorted first-order TRS. According to the external first-order termination prover, this system is indeed terminating: || proof of resources/system.trs || # AProVE Commit ID: d84c10301d352dfd14de2104819581f4682260f5 fuhs 20130616 || || || Termination w.r.t. Q of the given QTRS could be proven: || || (0) QTRS || (1) QTRSRRRProof [EQUIVALENT] || (2) QTRS || (3) RisEmptyProof [EQUIVALENT] || (4) YES || || || ---------------------------------------- || || (0) || Obligation: || Q restricted rewrite system: || The TRS R consists of the following rules: || || app(nil, %X) -> %X || app(cons(%X, %Y), %Z) -> cons(%X, app(%Y, %Z)) || iconsc(%X, %Y) -> cons(%Y, %X) || || Q is empty. || || ---------------------------------------- || || (1) QTRSRRRProof (EQUIVALENT) || Used ordering: || Polynomial interpretation [POLO]: || || POL(app(x_1, x_2)) = 2 + 2*x_1 + x_2 || POL(cons(x_1, x_2)) = 1 + x_1 + x_2 || POL(iconsc(x_1, x_2)) = 2 + 2*x_1 + 2*x_2 || POL(nil) = 1 || With this ordering the following rules can be removed by the rule removal processor [LPAR04] because they are oriented strictly: || || app(nil, %X) -> %X || app(cons(%X, %Y), %Z) -> cons(%X, app(%Y, %Z)) || iconsc(%X, %Y) -> cons(%Y, %X) || || || || || ---------------------------------------- || || (2) || Obligation: || Q restricted rewrite system: || R is empty. || Q is empty. || || ---------------------------------------- || || (3) RisEmptyProof (EQUIVALENT) || The TRS R is empty. Hence, termination is trivially proven. || ---------------------------------------- || || (4) || YES || We use the dependency pair framework as described in [Kop12, Ch. 6/7], with dynamic dependency pairs. We thus obtain the following dependency pair problem (P_0, R_0, minimal, formative): Dependency Pairs P_0: 0] foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) =#> foldl#(/\z./\u.X(z, u), X(Y, Z), U) 1] foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) =#> X(z, u) 2] foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) =#> X(Y, Z) 3] reverse#(X) =#> foldl#(/\x./\y.iconsc(x, y), nil, X) 4] reverse#(X) =#> iconsc#(x, y) 5] reverse1#(X) =#> foldl#(/\x./\y.app(cons(y, nil), x), nil, X) 6] reverse1#(X) =#> app#(cons(x, nil), y) Rules R_0: app(nil, X) => X app(cons(X, Y), Z) => cons(X, app(Y, Z)) foldl(/\x./\y.X(x, y), Y, nil) => Y foldl(/\x./\y.X(x, y), Y, cons(Z, U)) => foldl(/\z./\u.X(z, u), X(Y, Z), U) iconsc(X, Y) => cons(Y, X) reverse(X) => foldl(/\x./\y.iconsc(x, y), nil, X) reverse1(X) => foldl(/\x./\y.app(cons(y, nil), x), nil, X) Thus, the original system is terminating if (P_0, R_0, minimal, formative) is finite. We consider the dependency pair problem (P_0, R_0, minimal, formative). We place the elements of P in a dependency graph approximation G (see e.g. [Kop12, Thm. 7.27, 7.29], as follows: * 0 : 0, 1, 2 * 1 : 0, 1, 2, 3, 4, 5, 6 * 2 : 0, 1, 2, 3, 4, 5, 6 * 3 : 0, 1, 2 * 4 : * 5 : 0, 1, 2 * 6 : This graph has the following strongly connected components: P_1: foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) =#> foldl#(/\z./\u.X(z, u), X(Y, Z), U) foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) =#> X(z, u) foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) =#> X(Y, Z) reverse#(X) =#> foldl#(/\x./\y.iconsc(x, y), nil, X) reverse1#(X) =#> foldl#(/\x./\y.app(cons(y, nil), x), nil, X) By [Kop12, Thm. 7.31], we may replace any dependency pair problem (P_0, R_0, m, f) by (P_1, R_0, m, f). Thus, the original system is terminating if (P_1, R_0, minimal, formative) is finite. We consider the dependency pair problem (P_1, R_0, minimal, formative). We will use the reduction pair processor [Kop12, Thm. 7.16]. As the system is abstraction-simple and the formative flag is set, it suffices to find a tagged reduction pair [Kop12, Def. 6.70]. Thus, we must orient: foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) >? foldl#(/\z./\u.X(z, u), X(Y, Z), U) foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) >? X(~c0, ~c1) foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) >? X(Y, Z) reverse#(X) >? foldl#(/\x./\y.iconsc-(x, y), nil, X) reverse1#(X) >? foldl#(/\x./\y.app-(cons-(y, nil), x), nil, X) app(nil, X) >= X app(cons(X, Y), Z) >= cons(X, app(Y, Z)) foldl(/\x./\y.X(x, y), Y, nil) >= Y foldl(/\x./\y.X(x, y), Y, cons(Z, U)) >= foldl(/\z./\u.X(z, u), X(Y, Z), U) iconsc(X, Y) >= cons(Y, X) reverse(X) >= foldl(/\x./\y.iconsc-(x, y), nil, X) reverse1(X) >= foldl(/\x./\y.app-(cons-(y, nil), x), nil, X) app-(X, Y) >= app(X, Y) cons-(X, Y) >= cons(X, Y) iconsc-(X, Y) >= iconsc(X, Y) We apply [Kop12, Thm. 6.75] and use the following argument functions: pi( iconsc(X, Y) ) = #argfun-iconsc#(cons(Y, X)) pi( reverse(X) ) = #argfun-reverse#(foldl(/\x./\y.iconsc-(x, y), nil, X)) pi( reverse1(X) ) = #argfun-reverse1#(foldl(/\x./\y.app-(cons-(y, nil), x), nil, X)) pi( reverse1#(X) ) = #argfun-reverse1##(foldl#(/\x./\y.app-(cons-(y, nil), x), nil, X)) pi( reverse#(X) ) = #argfun-reverse##(foldl#(/\x./\y.iconsc-(x, y), nil, X)) Since this representation is not advantageous for the higher-order recursive path ordering, we present the strict requirements in their unextended form, which is not problematic since for any F, s and substituion gamma: (F s)gamma beta-reduces to F(s)gamma.) We use a recursive path ordering as defined in [Kop12, Chapter 5]. Argument functions: [[#argfun-iconsc#(x_1)]] = x_1 [[#argfun-reverse1##(x_1)]] = x_1 [[foldl(x_1, x_2, x_3)]] = foldl(x_1, x_3, x_2) [[foldl#(x_1, x_2, x_3)]] = foldl#(x_3, x_1, x_2) [[reverse(x_1)]] = x_1 [[reverse1(x_1)]] = x_1 [[reverse1#(x_1)]] = x_1 [[reverse#(x_1)]] = x_1 [[~c0]] = _|_ [[~c1]] = _|_ We choose Lex = {foldl, foldl#} and Mul = {#argfun-reverse#, #argfun-reverse1#, #argfun-reverse##, app, app-, cons, cons-, iconsc, iconsc-, nil}, and the following precedence: iconsc > #argfun-reverse# > iconsc- > cons- > #argfun-reverse1# > app = app- > foldl# > nil > foldl > #argfun-reverse## > cons Taking the argument function into account, and fixing the greater / greater equal choices, the constraints can be denoted as follows: foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) > foldl#(/\x./\y.X(x, y), X(Y, Z), U) foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) >= X(_|_, _|_) foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) > X(Y, Z) #argfun-reverse##(foldl#(/\x./\y.iconsc-(x, y), nil, X)) >= foldl#(/\x./\y.iconsc-(x, y), nil, X) foldl#(/\x./\y.app-(cons-(y, nil), x), nil, X) >= foldl#(/\x./\y.app-(cons-(y, nil), x), nil, X) app(nil, X) >= X app(cons(X, Y), Z) >= cons(X, app(Y, Z)) foldl(/\x./\y.X(x, y), Y, nil) >= Y foldl(/\x./\y.X(x, y), Y, cons(Z, U)) >= foldl(/\x./\y.X(x, y), X(Y, Z), U) cons(X, Y) >= cons(X, Y) #argfun-reverse#(foldl(/\x./\y.iconsc-(x, y), nil, X)) >= foldl(/\x./\y.iconsc-(x, y), nil, X) #argfun-reverse1#(foldl(/\x./\y.app-(cons-(y, nil), x), nil, X)) >= foldl(/\x./\y.app-(cons-(y, nil), x), nil, X) app-(X, Y) >= app(X, Y) cons-(X, Y) >= cons(X, Y) iconsc-(X, Y) >= cons(Y, X) With these choices, we have: 1] foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) > foldl#(/\x./\y.X(x, y), X(Y, Z), U) because [2], by definition 2] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= foldl#(/\x./\y.X(x, y), X(Y, Z), U) because [3], [6], [13] and [21], by (Stat) 3] cons(Z, U) > U because [4], by definition 4] cons*(Z, U) >= U because [5], by (Select) 5] U >= U by (Meta) 6] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= /\x./\y.X(x, y) because [7], by (F-Abs) 7] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U), z) >= /\x.X(z, x) because [8], by (Select) 8] /\x.X(foldl#*(/\y./\v.X(y, v), Y, cons(Z, U), z), x) >= /\x.X(z, x) because [9], by (Abs) 9] X(foldl#*(/\x./\y.X(x, y), Y, cons(Z, U), z), u) >= X(z, u) because [10] and [12], by (Meta) 10] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U), z) >= z because [11], by (Select) 11] z >= z by (Var) 12] u >= u by (Var) 13] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= X(Y, Z) because [14], by (Select) 14] X(foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)), foldl#*(/\v./\w.X(v, w), Y, cons(Z, U))) >= X(Y, Z) because [15] and [17], by (Meta) 15] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= Y because [16], by (Select) 16] Y >= Y by (Meta) 17] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= Z because [18], by (Select) 18] cons(Z, U) >= Z because [19], by (Star) 19] cons*(Z, U) >= Z because [20], by (Select) 20] Z >= Z by (Meta) 21] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= U because [22], by (Select) 22] cons(Z, U) >= U because [4], by (Star) 23] foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) >= X(_|_, _|_) because [24], by (Star) 24] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= X(_|_, _|_) because [25], by (Select) 25] X(foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)), foldl#*(/\z./\u.X(z, u), Y, cons(Z, U))) >= X(_|_, _|_) because [26] and [27], by (Meta) 26] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= _|_ by (Bot) 27] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= _|_ by (Bot) 28] foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) > X(Y, Z) because [13], by definition 29] #argfun-reverse##(foldl#(/\x./\y.iconsc-(x, y), nil, X)) >= foldl#(/\x./\y.iconsc-(x, y), nil, X) because [30], by (Star) 30] #argfun-reverse##*(foldl#(/\x./\y.iconsc-(x, y), nil, X)) >= foldl#(/\x./\y.iconsc-(x, y), nil, X) because [31], by (Select) 31] foldl#(/\x./\y.iconsc-(x, y), nil, X) >= foldl#(/\x./\y.iconsc-(x, y), nil, X) because [32], [37] and [38], by (Fun) 32] /\x./\z.iconsc-(x, z) >= /\x./\z.iconsc-(x, z) because [33], by (Abs) 33] /\z.iconsc-(y, z) >= /\z.iconsc-(y, z) because [34], by (Abs) 34] iconsc-(y, x) >= iconsc-(y, x) because iconsc- in Mul, [35] and [36], by (Fun) 35] y >= y by (Var) 36] x >= x by (Var) 37] nil >= nil by (Fun) 38] X >= X by (Meta) 39] foldl#(/\x./\y.app-(cons-(y, nil), x), nil, X) >= foldl#(/\x./\y.app-(cons-(y, nil), x), nil, X) because [40], [37] and [46], by (Fun) 40] /\x./\z.app-(cons-(z, nil), x) >= /\x./\z.app-(cons-(z, nil), x) because [41], by (Abs) 41] /\z.app-(cons-(z, nil), y) >= /\z.app-(cons-(z, nil), y) because [42], by (Abs) 42] app-(cons-(x, nil), y) >= app-(cons-(x, nil), y) because app- in Mul, [43] and [45], by (Fun) 43] cons-(x, nil) >= cons-(x, nil) because cons- in Mul, [44] and [37], by (Fun) 44] x >= x by (Var) 45] y >= y by (Var) 46] X >= X by (Meta) 47] app(nil, X) >= X because [48], by (Star) 48] app*(nil, X) >= X because [49], by (Select) 49] X >= X by (Meta) 50] app(cons(X, Y), Z) >= cons(X, app(Y, Z)) because [51], by (Star) 51] app*(cons(X, Y), Z) >= cons(X, app(Y, Z)) because app > cons, [52] and [56], by (Copy) 52] app*(cons(X, Y), Z) >= X because [53], by (Select) 53] cons(X, Y) >= X because [54], by (Star) 54] cons*(X, Y) >= X because [55], by (Select) 55] X >= X by (Meta) 56] app*(cons(X, Y), Z) >= app(Y, Z) because app in Mul, [57] and [60], by (Stat) 57] cons(X, Y) > Y because [58], by definition 58] cons*(X, Y) >= Y because [59], by (Select) 59] Y >= Y by (Meta) 60] Z >= Z by (Meta) 61] foldl(/\x./\y.X(x, y), Y, nil) >= Y because [62], by (Star) 62] foldl*(/\x./\y.X(x, y), Y, nil) >= Y because [63], by (Select) 63] Y >= Y by (Meta) 64] foldl(/\x./\y.X(x, y), Y, cons(Z, U)) >= foldl(/\x./\y.X(x, y), X(Y, Z), U) because [65], by (Star) 65] foldl*(/\x./\y.X(x, y), Y, cons(Z, U)) >= foldl(/\x./\y.X(x, y), X(Y, Z), U) because [66], [3], [71], [72] and [76], by (Stat) 66] /\x./\z.X(x, z) >= /\x./\z.X(x, z) because [67], by (Abs) 67] /\z.X(y, z) >= /\z.X(y, z) because [68], by (Abs) 68] X(y, x) >= X(y, x) because [69] and [70], by (Meta) 69] y >= y by (Var) 70] x >= x by (Var) 71] foldl*(/\z./\u.X(z, u), Y, cons(Z, U)) >= /\z./\u.X(z, u) because [66], by (Select) 72] foldl*(/\z./\u.X(z, u), Y, cons(Z, U)) >= X(Y, Z) because [73], by (Select) 73] X(foldl*(/\z./\u.X(z, u), Y, cons(Z, U)), foldl*(/\v./\w.X(v, w), Y, cons(Z, U))) >= X(Y, Z) because [74] and [75], by (Meta) 74] foldl*(/\z./\u.X(z, u), Y, cons(Z, U)) >= Y because [16], by (Select) 75] foldl*(/\z./\u.X(z, u), Y, cons(Z, U)) >= Z because [18], by (Select) 76] foldl*(/\z./\u.X(z, u), Y, cons(Z, U)) >= U because [22], by (Select) 77] cons(X, Y) >= cons(X, Y) because cons in Mul, [78] and [79], by (Fun) 78] X >= X by (Meta) 79] Y >= Y by (Meta) 80] #argfun-reverse#(foldl(/\x./\y.iconsc-(x, y), nil, X)) >= foldl(/\x./\y.iconsc-(x, y), nil, X) because [81], by (Star) 81] #argfun-reverse#*(foldl(/\x./\y.iconsc-(x, y), nil, X)) >= foldl(/\x./\y.iconsc-(x, y), nil, X) because [82], by (Select) 82] foldl(/\x./\y.iconsc-(x, y), nil, X) >= foldl(/\x./\y.iconsc-(x, y), nil, X) because [32], [37] and [38], by (Fun) 83] #argfun-reverse1#(foldl(/\x./\y.app-(cons-(y, nil), x), nil, X)) >= foldl(/\x./\y.app-(cons-(y, nil), x), nil, X) because [84], by (Star) 84] #argfun-reverse1#*(foldl(/\x./\y.app-(cons-(y, nil), x), nil, X)) >= foldl(/\x./\y.app-(cons-(y, nil), x), nil, X) because [85], by (Select) 85] foldl(/\x./\y.app-(cons-(y, nil), x), nil, X) >= foldl(/\x./\y.app-(cons-(y, nil), x), nil, X) because [40], [37] and [46], by (Fun) 86] app-(X, Y) >= app(X, Y) because app- = app, app- in Mul, [87] and [88], by (Fun) 87] X >= X by (Meta) 88] Y >= Y by (Meta) 89] cons-(X, Y) >= cons(X, Y) because [90], by (Star) 90] cons-*(X, Y) >= cons(X, Y) because cons- > cons, [91] and [93], by (Copy) 91] cons-*(X, Y) >= X because [92], by (Select) 92] X >= X by (Meta) 93] cons-*(X, Y) >= Y because [94], by (Select) 94] Y >= Y by (Meta) 95] iconsc-(X, Y) >= cons(Y, X) because [96], by (Star) 96] iconsc-*(X, Y) >= cons(Y, X) because iconsc- > cons, [97] and [99], by (Copy) 97] iconsc-*(X, Y) >= Y because [98], by (Select) 98] Y >= Y by (Meta) 99] iconsc-*(X, Y) >= X because [100], by (Select) 100] X >= X by (Meta) By the observations in [Kop12, Sec. 6.6], this reduction pair suffices; we may thus replace the dependency pair problem (P_1, R_0, minimal, formative) by (P_2, R_0, minimal, formative), where P_2 consists of: foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) =#> X(z, u) reverse#(X) =#> foldl#(/\x./\y.iconsc(x, y), nil, X) reverse1#(X) =#> foldl#(/\x./\y.app(cons(y, nil), x), nil, X) Thus, the original system is terminating if (P_2, R_0, minimal, formative) is finite. We consider the dependency pair problem (P_2, R_0, minimal, formative). We will use the reduction pair processor [Kop12, Thm. 7.16]. As the system is abstraction-simple and the formative flag is set, it suffices to find a tagged reduction pair [Kop12, Def. 6.70]. Thus, we must orient: foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) >? X(~c0, ~c1) reverse#(X) >? foldl#(/\x./\y.iconsc-(x, y), nil, X) reverse1#(X) >? foldl#(/\x./\y.app-(cons-(y, nil), x), nil, X) app(nil, X) >= X app(cons(X, Y), Z) >= cons(X, app(Y, Z)) foldl(/\x./\y.X(x, y), Y, nil) >= Y foldl(/\x./\y.X(x, y), Y, cons(Z, U)) >= foldl(/\z./\u.X(z, u), X(Y, Z), U) iconsc(X, Y) >= cons(Y, X) reverse(X) >= foldl(/\x./\y.iconsc-(x, y), nil, X) reverse1(X) >= foldl(/\x./\y.app-(cons-(y, nil), x), nil, X) app-(X, Y) >= app(X, Y) cons-(X, Y) >= cons(X, Y) iconsc-(X, Y) >= iconsc(X, Y) We apply [Kop12, Thm. 6.75] and use the following argument functions: pi( iconsc(X, Y) ) = #argfun-iconsc#(cons(Y, X)) pi( reverse(X) ) = #argfun-reverse#(foldl(/\x./\y.iconsc-(x, y), nil, X)) pi( reverse1(X) ) = #argfun-reverse1#(foldl(/\x./\y.app-(cons-(y, nil), x), nil, X)) pi( reverse1#(X) ) = #argfun-reverse1##(foldl#(/\x./\y.app-(cons-(y, nil), x), nil, X)) pi( reverse#(X) ) = #argfun-reverse##(foldl#(/\x./\y.iconsc-(x, y), nil, X)) Since this representation is not advantageous for the higher-order recursive path ordering, we present the strict requirements in their unextended form, which is not problematic since for any F, s and substituion gamma: (F s)gamma beta-reduces to F(s)gamma.) We use a recursive path ordering as defined in [Kop12, Chapter 5]. Argument functions: [[#argfun-reverse#(x_1)]] = x_1 [[cons(x_1, x_2)]] = cons(x_2, x_1) [[foldl(x_1, x_2, x_3)]] = foldl(x_3, x_1, x_2) [[nil]] = _|_ [[reverse(x_1)]] = x_1 [[reverse1(x_1)]] = x_1 [[reverse#(x_1)]] = x_1 [[~c0]] = _|_ [[~c1]] = _|_ We choose Lex = {#argfun-iconsc#, cons, foldl} and Mul = {#argfun-reverse1#, #argfun-reverse1##, #argfun-reverse##, app, app-, cons-, foldl#, iconsc, iconsc-, reverse1#}, and the following precedence: #argfun-reverse1# > #argfun-reverse1## > app- > app > foldl > #argfun-reverse## > iconsc- > foldl# > cons- > reverse1# > #argfun-iconsc# = cons > iconsc Taking the argument function into account, and fixing the greater / greater equal choices, the constraints can be denoted as follows: foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) > X(_|_, _|_) #argfun-reverse##(foldl#(/\x./\y.iconsc-(x, y), _|_, X)) >= foldl#(/\x./\y.iconsc-(x, y), _|_, X) #argfun-reverse1##(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X) app(_|_, X) >= X app(cons(X, Y), Z) >= cons(X, app(Y, Z)) foldl(/\x./\y.X(x, y), Y, _|_) >= Y foldl(/\x./\y.X(x, y), Y, cons(Z, U)) >= foldl(/\x./\y.X(x, y), X(Y, Z), U) #argfun-iconsc#(cons(X, Y)) >= cons(X, Y) foldl(/\x./\y.iconsc-(x, y), _|_, X) >= foldl(/\x./\y.iconsc-(x, y), _|_, X) #argfun-reverse1#(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X) app-(X, Y) >= app(X, Y) cons-(X, Y) >= cons(X, Y) iconsc-(X, Y) >= #argfun-iconsc#(cons(Y, X)) With these choices, we have: 1] foldl#(/\x./\y.X(x, y), Y, cons(Z, U)) > X(_|_, _|_) because [2], by definition 2] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= X(_|_, _|_) because [3], by (Select) 3] X(foldl#*(/\x./\y.X(x, y), Y, cons Z U), foldl#*(/\z./\u.X(z, u), Y, cons)) >= X(_|_, _|_) because [4] and [5], by (Meta) 4] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= _|_ by (Bot) 5] foldl#*(/\x./\y.X(x, y), Y, cons(Z, U)) >= _|_ by (Bot) 6] #argfun-reverse##(foldl#(/\x./\y.iconsc-(x, y), _|_, X)) >= foldl#(/\x./\y.iconsc-(x, y), _|_, X) because [7], by (Star) 7] #argfun-reverse##*(foldl#(/\x./\y.iconsc-(x, y), _|_, X)) >= foldl#(/\x./\y.iconsc-(x, y), _|_, X) because #argfun-reverse## > foldl#, [8], [15] and [16], by (Copy) 8] #argfun-reverse##*(foldl#(/\x./\y.iconsc-(x, y), _|_, X)) >= /\x./\y.iconsc-(x, y) because [9], by (F-Abs) 9] #argfun-reverse##*(foldl#(/\x./\y.iconsc-(x, y), _|_, X), z) >= /\x.iconsc-(z, x) because [10], by (F-Abs) 10] #argfun-reverse##*(foldl#(/\x./\y.iconsc-(x, y), _|_, X), z, u) >= iconsc-(z, u) because #argfun-reverse## > iconsc-, [11] and [13], by (Copy) 11] #argfun-reverse##*(foldl#(/\x./\y.iconsc-(x, y), _|_, X), z, u) >= z because [12], by (Select) 12] z >= z by (Var) 13] #argfun-reverse##*(foldl#(/\x./\y.iconsc-(x, y), _|_, X), z, u) >= u because [14], by (Select) 14] u >= u by (Var) 15] #argfun-reverse##*(foldl#(/\x./\y.iconsc-(x, y), _|_, X)) >= _|_ by (Bot) 16] #argfun-reverse##*(foldl#(/\x./\y.iconsc-(x, y), _|_, X)) >= X because [17], by (Select) 17] foldl#(/\x./\y.iconsc-(x, y), _|_, X) >= X because [18], by (Star) 18] foldl#*(/\x./\y.iconsc-(x, y), _|_, X) >= X because [19], by (Select) 19] X >= X by (Meta) 20] #argfun-reverse1##(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X) because [21], by (Star) 21] #argfun-reverse1##*(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X) because #argfun-reverse1## > foldl#, [22], [31] and [32], by (Copy) 22] #argfun-reverse1##*(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= /\x./\y.app-(cons-(y, _|_), x) because [23], by (F-Abs) 23] #argfun-reverse1##*(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z) >= /\x.app-(cons-(x, _|_), z) because [24], by (F-Abs) 24] #argfun-reverse1##*(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z, u) >= app-(cons-(u, _|_), z) because #argfun-reverse1## > app-, [25] and [29], by (Copy) 25] #argfun-reverse1##*(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z, u) >= cons-(u, _|_) because #argfun-reverse1## > cons-, [26] and [28], by (Copy) 26] #argfun-reverse1##*(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z, u) >= u because [27], by (Select) 27] u >= u by (Var) 28] #argfun-reverse1##*(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z, u) >= _|_ by (Bot) 29] #argfun-reverse1##*(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z, u) >= z because [30], by (Select) 30] z >= z by (Var) 31] #argfun-reverse1##*(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= _|_ by (Bot) 32] #argfun-reverse1##*(foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= X because [33], by (Select) 33] foldl#(/\x./\y.app-(cons-(y, _|_), x), _|_, X) >= X because [34], by (Star) 34] foldl#*(/\x./\y.app-(cons-(y, _|_), x), _|_, X) >= X because [35], by (Select) 35] X >= X by (Meta) 36] app(_|_, X) >= X because [37], by (Star) 37] app*(_|_, X) >= X because [38], by (Select) 38] X >= X by (Meta) 39] app(cons(X, Y), Z) >= cons(X, app(Y, Z)) because [40], by (Star) 40] app*(cons(X, Y), Z) >= cons(X, app(Y, Z)) because app > cons, [41] and [45], by (Copy) 41] app*(cons(X, Y), Z) >= X because [42], by (Select) 42] cons(X, Y) >= X because [43], by (Star) 43] cons*(X, Y) >= X because [44], by (Select) 44] X >= X by (Meta) 45] app*(cons(X, Y), Z) >= app(Y, Z) because app in Mul, [46] and [49], by (Stat) 46] cons(X, Y) > Y because [47], by definition 47] cons*(X, Y) >= Y because [48], by (Select) 48] Y >= Y by (Meta) 49] Z >= Z by (Meta) 50] foldl(/\x./\y.X(x, y), Y, _|_) >= Y because [51], by (Star) 51] foldl*(/\x./\y.X(x, y), Y, _|_) >= Y because [52], by (Select) 52] Y >= Y by (Meta) 53] foldl(/\x./\y.X(x, y), Y, cons(Z, U)) >= foldl(/\x./\y.X(x, y), X(Y, Z), U) because [54], by (Star) 54] foldl*(/\x./\y.X(x, y), Y, cons(Z, U)) >= foldl(/\x./\y.X(x, y), X(Y, Z), U) because [55], [58], [66] and [74], by (Stat) 55] cons(Z, U) > U because [56], by definition 56] cons*(Z, U) >= U because [57], by (Select) 57] U >= U by (Meta) 58] foldl*(/\x./\y.X(x, y), Y, cons(Z, U)) >= /\x./\y.X(x, y) because [59], by (F-Abs) 59] foldl*(/\x./\y.X(x, y), Y, cons(Z, U), z) >= /\x.X(z, x) because [60], by (F-Abs) 60] foldl*(/\x./\y.X(x, y), Y, cons(Z, U), z, u) >= X(z, u) because [61], by (Select) 61] X(foldl*(/\x./\y.X(x, y), Y, cons Z U, z, u), foldl*(/\v./\w.X(v, w), Y, cons, z, u)) >= X(z, u) because [62] and [64], by (Meta) 62] foldl*(/\x./\y.X(x, y), Y, cons(Z, U), z, u) >= z because [63], by (Select) 63] z >= z by (Var) 64] foldl*(/\x./\y.X(x, y), Y, cons(Z, U), z, u) >= u because [65], by (Select) 65] u >= u by (Var) 66] foldl*(/\x./\y.X(x, y), Y, cons(Z, U)) >= X(Y, Z) because [67], by (Select) 67] X(foldl*(/\x./\y.X(x, y), Y, cons Z U), foldl*(/\v./\w.X(v, w), Y, cons)) >= X(Y, Z) because [68] and [70], by (Meta) 68] foldl*(/\x./\y.X(x, y), Y, cons(Z, U)) >= Y because [69], by (Select) 69] Y >= Y by (Meta) 70] foldl*(/\x./\y.X(x, y), Y, cons(Z, U)) >= Z because [71], by (Select) 71] cons(Z, U) >= Z because [72], by (Star) 72] cons*(Z, U) >= Z because [73], by (Select) 73] Z >= Z by (Meta) 74] foldl*(/\x./\y.X(x, y), Y, cons(Z, U)) >= U because [75], by (Select) 75] cons(Z, U) >= U because [56], by (Star) 76] #argfun-iconsc#(cons(X, Y)) >= cons(X, Y) because [77], by (Star) 77] #argfun-iconsc#*(cons(X, Y)) >= cons(X, Y) because #argfun-iconsc# = cons, [78], [81] and [85], by (Stat) 78] cons(X, Y) > Y because [79], by definition 79] cons*(X, Y) >= Y because [80], by (Select) 80] Y >= Y by (Meta) 81] #argfun-iconsc#*(cons(X, Y)) >= X because [82], by (Select) 82] cons(X, Y) >= X because [83], by (Star) 83] cons*(X, Y) >= X because [84], by (Select) 84] X >= X by (Meta) 85] #argfun-iconsc#*(cons(X, Y)) >= Y because [86], by (Select) 86] cons(X, Y) >= Y because [79], by (Star) 87] foldl(/\x./\y.iconsc-(x, y), _|_, X) >= foldl(/\x./\y.iconsc-(x, y), _|_, X) because [88], [93] and [94], by (Fun) 88] /\x./\z.iconsc-(x, z) >= /\x./\z.iconsc-(x, z) because [89], by (Abs) 89] /\z.iconsc-(y, z) >= /\z.iconsc-(y, z) because [90], by (Abs) 90] iconsc-(y, x) >= iconsc-(y, x) because iconsc- in Mul, [91] and [92], by (Fun) 91] y >= y by (Var) 92] x >= x by (Var) 93] _|_ >= _|_ by (Bot) 94] X >= X by (Meta) 95] #argfun-reverse1#(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X) because [96], by (Star) 96] #argfun-reverse1#*(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X) because #argfun-reverse1# > foldl, [97], [106] and [107], by (Copy) 97] #argfun-reverse1#*(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= /\x./\y.app-(cons-(y, _|_), x) because [98], by (F-Abs) 98] #argfun-reverse1#*(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z) >= /\x.app-(cons-(x, _|_), z) because [99], by (F-Abs) 99] #argfun-reverse1#*(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z, u) >= app-(cons-(u, _|_), z) because #argfun-reverse1# > app-, [100] and [104], by (Copy) 100] #argfun-reverse1#*(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z, u) >= cons-(u, _|_) because #argfun-reverse1# > cons-, [101] and [103], by (Copy) 101] #argfun-reverse1#*(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z, u) >= u because [102], by (Select) 102] u >= u by (Var) 103] #argfun-reverse1#*(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z, u) >= _|_ by (Bot) 104] #argfun-reverse1#*(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X), z, u) >= z because [105], by (Select) 105] z >= z by (Var) 106] #argfun-reverse1#*(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= _|_ by (Bot) 107] #argfun-reverse1#*(foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X)) >= X because [108], by (Select) 108] foldl(/\x./\y.app-(cons-(y, _|_), x), _|_, X) >= X because [109], by (Star) 109] foldl*(/\x./\y.app-(cons-(y, _|_), x), _|_, X) >= X because [35], by (Select) 110] app-(X, Y) >= app(X, Y) because [111], by (Star) 111] app-*(X, Y) >= app(X, Y) because app- > app, [112] and [114], by (Copy) 112] app-*(X, Y) >= X because [113], by (Select) 113] X >= X by (Meta) 114] app-*(X, Y) >= Y because [115], by (Select) 115] Y >= Y by (Meta) 116] cons-(X, Y) >= cons(X, Y) because [117], by (Star) 117] cons-*(X, Y) >= cons(X, Y) because cons- > cons, [118] and [120], by (Copy) 118] cons-*(X, Y) >= X because [119], by (Select) 119] X >= X by (Meta) 120] cons-*(X, Y) >= Y because [121], by (Select) 121] Y >= Y by (Meta) 122] iconsc-(X, Y) >= #argfun-iconsc#(cons(Y, X)) because [123], by (Star) 123] iconsc-*(X, Y) >= #argfun-iconsc#(cons(Y, X)) because iconsc- > #argfun-iconsc# and [124], by (Copy) 124] iconsc-*(X, Y) >= cons(Y, X) because iconsc- > cons, [125] and [127], by (Copy) 125] iconsc-*(X, Y) >= Y because [126], by (Select) 126] Y >= Y by (Meta) 127] iconsc-*(X, Y) >= X because [128], by (Select) 128] X >= X by (Meta) By the observations in [Kop12, Sec. 6.6], this reduction pair suffices; we may thus replace the dependency pair problem (P_2, R_0, minimal, formative) by (P_3, R_0, minimal, formative), where P_3 consists of: reverse#(X) =#> foldl#(/\x./\y.iconsc(x, y), nil, X) reverse1#(X) =#> foldl#(/\x./\y.app(cons(y, nil), x), nil, X) Thus, the original system is terminating if (P_3, R_0, minimal, formative) is finite. We consider the dependency pair problem (P_3, R_0, minimal, formative). We place the elements of P in a dependency graph approximation G (see e.g. [Kop12, Thm. 7.27, 7.29], as follows: * 0 : * 1 : This graph has no strongly connected components. By [Kop12, Thm. 7.31], this implies finiteness of the dependency pair problem. As all dependency pair problems were succesfully simplified with sound (and complete) processors until nothing remained, we conclude termination. +++ Citations +++ [Kop11] C. Kop. Simplifying Algebraic Functional Systems. In Proceedings of CAI 2011, volume 6742 of LNCS. 201--215, Springer, 2011. [Kop12] C. Kop. Higher Order Termination. PhD Thesis, 2012.