1-- Induction on finitely supported coefficient maps by zero, terms, and addition.2-- Part of Cumulus, the Grace17 mathematics library.3-- Copyright (c) 2026 Grant Passmore.4-- Released under the Apache License 2.0. See LICENSE in the repository root.5-- Authors: Grant Passmore67module Grace.Cumulus.Algebra.CoefficientInduction8import CoefficientSingle910defgraph coefficientErase (I A z f j : Set) (i ∈ I) : A := singleValue(A, f(i), z, j, i)11requires zeroIn : z ∈ A12requires function : f : I → A13proof14have value := FunctionBetween.apply_closed at f, I, A, i with*15exact singleValue.closed at A, f(i), z, j, i with*1617theorem coefficientErase.same (I A z f j : Set)18requires zeroIn : z ∈ A19requires function : f : I → A20requires index : j ∈ I21shows coefficientErase(I, A, z, f, j)(j) = z22proof23have coefficient := FunctionBetween.apply_closed with*24have value := coefficientErase.value at I, A, z, f, j, j with*25have same : j = j byrfl26have selected := singleValue.same at A, f(j), z, j, j with*27cc2829theorem coefficientErase.other (I A z f j i : Set)30requires zeroIn : z ∈ A31requires function : f : I → A32requires index : i ∈ I33requires different : i ≠ j34shows coefficientErase(I, A, z, f, j)(i) = f(i)35proof36have coefficient := FunctionBetween.apply_closed with*37have value := coefficientErase.value at I, A, z, f, j, i with*38have selected := singleValue.other at A, f(i), z, j, i with*39cc4041theorem coefficientErase.support (I A z f j : Set)42requires zeroIn : z ∈ A43requires function : f : I → A44shows functionSupport(coefficientErase(I, A, z, f, j), I, z) ⊆ functionSupport(f, I, z) ∖ {j}45proof46intros i hi47have data := functionSupport.membership.forward with hi48have different : i ≠ j49intro equal50have erased := coefficientErase.same at I, A, z, f, i with*51have impossible : coefficientErase(I, A, z, f, j)(i) = z bycc52exact data.right with impossible53have value := coefficientErase.other with*54apply difference.membership.backward55constructor56 . apply functionSupport.membership.backward at f, I, z, i57 rwa value at data58 . settlewith singleton.membership5960section Rings61variable (I A add zero neg mul one : Set)62hypothesisring : IsCommRing(A, add, zero, neg, mul, one)63notationring R := (A, add, zero, neg, mul, one)6465theorem coefficientErase.restore (f j : Set)66requires function : f : I → A67requires index : j ∈ I68shows coefficientAdd(I, A, add, zero, neg, mul, one, coefficientSingle(I, A, zero, f(j), j), coefficientErase(I, A, zero, f, j)) = f69proof70have ordinary := IsCommRing.ring withring71have zeroIn := IsRing.zero_in_carrier with ordinary72have coefficient := FunctionBetween.apply_closed with*73have single := coefficientSingle.function at I, A, zero, f(j), j with*74have erased := coefficientErase.function at I, A, zero, f, j with*75have restored := coefficientAdd.function at I, A, add, zero, neg, mul, one, coefficientSingle(I, A, zero, f(j), j), coefficientErase(I, A, zero, f, j) with*76apply FunctionBetween.ext with restored, function77intros i hi78have value := FunctionBetween.apply_closed at f, I, A, i with*79have sum := coefficientAdd.value at I, A, add, zero, neg, mul, one, coefficientSingle(I, A, zero, f(j), j), coefficientErase(I, A, zero, f, j), i with*80rw sum81have alternatives : i = j ∨ i ≠ j bytauto82cases alternatives with same | different83 . rw same84have value1 := coefficientSingle.same at I, A, zero, f(j), j with*85rw value186have value2 := coefficientErase.same at I, A, zero, f, j with*87rw value288ring89 . have singleOther := coefficientSingle.other with zeroIn, coefficient, different90rw singleOther91have value3 := coefficientErase.other with zeroIn, function, different92rw value393ring9495theorem coefficientMaps.generated_list (S : Set) (xs : List(I))96requires base : constantFunction(I, A, zero) ∈ S97requires step : ∀ a ∈ A, ∀ j ∈ I, ∀ f ∈ S, coefficientAdd(I, A, add, zero, neg, mul, one, coefficientSingle(I, A, zero, a, j), f) ∈ S98shows∀ f, FunctionBetween(f, I, A) → functionSupport(f, I, zero) ⊆ listSupport{I}(xs) → f ∈ S99proof100induction xs101| List.nil =>102intros f function covers103have ordinary := IsCommRing.ring withring104have zeroIn := IsRing.zero_in_carrier with ordinary105rw listSupport at covers106have zeroFunction := constantFunction.function at I, A, zero with*107have equal : f = constantFunction(I, A, zero)108apply FunctionBetween.ext with function, zeroFunction109intros i hi110have absent : ¬(i ∈ functionSupport(f, I, zero))111intro supported112have impossible := covers with i, supported113exactset.empty with impossible114have vanishes := functionSupport.outside at f, I, zero, i with*115have value := constantFunction.apply at I, A, i, zero with*116cc117 rwa equal118| List.cons(j, tail) using ih =>119intros f function covers120have ordinary := IsCommRing.ring withring121have zeroIn := IsRing.zero_in_carrier with ordinary122have index : j ∈ I byassumption123rw listSupport at covers124have erased := coefficientErase.function at I, A, zero, f, j with*125have support := coefficientErase.support at I, A, zero, f, j with*126have smaller : functionSupport(coefficientErase(I, A, zero, f, j), I, zero) ⊆ listSupport{I}(tail)127intros i hi128have data := support with i, hi129have difference := difference.membership.forward with data130have covered := covers with i, difference.left131have alternatives := insert.membership.forward with covered132cases alternatives with equal | old133 . have singleton : i ∈ {j}134simp135exfalso136exact difference.right with singleton137 . exact old138have rest := ih with coefficientErase(I, A, zero, f, j), erased, smaller139have coefficient := FunctionBetween.apply_closed at f, I, A, j with*140have next := step with f(j), coefficient, j, index, coefficientErase(I, A, zero, f, j), rest141have restore := coefficientErase.restore at I, A, add, zero, neg, mul, one, f, j with*142 rwa restore at next143144theorem coefficientMaps.induction (S f : Set)145requires map : CoefficientMap(f, I, A, zero)146requires base : constantFunction(I, A, zero) ∈ S147requires step : ∀ a ∈ A, ∀ j ∈ I, ∀ p ∈ S, coefficientAdd(I, A, add, zero, neg, mul, one, coefficientSingle(I, A, zero, a, j), p) ∈ S148shows f ∈ S149proof150obtain⟨xs, list, covers⟩:= CoefficientMap.support_list withring, map151have function := CoefficientMap.function with map152have generated := coefficientMaps.generated_list with*153exact generated with f, function, covers154155end Rings156