Zulip Chat Archive
Stream: Is there code for X?
Topic: subfamilies are linearly independent
Michael Stoll (Mar 25 2023 at 05:54):
I'm trying to prove some results in linear algebra (see this discussion), and I am having problems dealing with the API successfully. Right now, I am a bit stuck on this simple fact:
import linear_algebra.linear_independent
variables {F V ι : Type*} [field F] [add_comm_group V] [module F V]
lemma linear_idependent.subfamily {I J : set ι} (hJI : J ⊆ I) (v : ι → V)
(hI : linear_independent F (I.restrict v)) : linear_independent F (J.restrict v) := sorry
This looks like it should be simple (or even in the library), but so far I don't really see how to do it without tying myself in knots. Any suggestions?
Reid Barton (Mar 25 2023 at 06:08):
I would try starting with docs#inear_independent.comp
Michael Stoll (Mar 25 2023 at 06:10):
That's the conclusion I just reached myself:
lemma linear_idependent.subfamily {I J : set ι} (hJI : J ⊆ I) (v : ι → V)
(hI : linear_independent F (I.restrict v)) : linear_independent F (J.restrict v) :=
begin
rw (show J.restrict v = (I.restrict v) ∘ (set.inclusion hJI), from by {ext, simp}),
exact linear_independent.comp hI _ (set.inclusion_injective hJI),
end
Still, I'd expect this to be in mathlib...
Eric Wieser (Mar 25 2023 at 06:33):
Does the proof still work without the first tactic line?
Xavier Roblot (Mar 25 2023 at 06:44):
Did you try to use docs#linear_independent.mono?
Eric Wieser (Mar 25 2023 at 06:48):
docs#linear_independent.restrict_of_comp_subtype looks helpful too
Eric Wieser (Mar 25 2023 at 06:50):
Xavier Roblot said:
Did you try to use docs#linear_independent.mono?
Maybe this lemma should be generalized to take a v : ι → V
, with the current spelling being v = id
Michael Stoll (Mar 25 2023 at 16:39):
Eric Wieser said:
Does the proof still work without the first tactic line?
No:
type mismatch at application
hI.comp
term
hI
has type
linear_independent F (I.restrict v)
but is expected to have type
linear_independent F v
(I think I tried that first...)
Michael Stoll (Mar 25 2023 at 16:41):
Xavier Roblot said:
Did you try to use docs#linear_independent.mono?
Then you first have to convert to the identity family on the images. I don't think this will be simpler.
(See @Eric Wieser's remark.)
Michael Stoll (Mar 25 2023 at 16:46):
Eric Wieser said:
docs#linear_independent.restrict_of_comp_subtype looks helpful too
refine linear_independent.restrict_of_comp_subtype _,
leads to the goal linear_independent F (v ∘ (coe :↥J → ι))
. I think the problem here is that set.inclusion hJI
is not a coercion, so you cannot directly use linear_independent.restrict_of_comp_subtype
(you'd have to replace ι
by ↥I
to be able to make use of the assumption).
Michael Stoll (Mar 29 2023 at 04:46):
Now for the next level:
lemma linear_independent.quotient₁ {I J : set ι} (hIJ : disjoint I J) {v : ι → V}
(hv : linear_independent F ((I ∪ J).restrict v)) :
linear_independent F (J.restrict ((mkq (span F (v '' I))) ∘ v)) :=
I guess the way to go is to use linear_independent.map
and linear_independent.disjoint_span_image
. But to get there was not so easy...
The best I have come up with is the following:
import linear_algebra.linear_independent
import linear_algebra.quotient
namespace set
lemma restrict_image_union_left {α β} (s t : set α) (f : α → β) :
f '' s = ((s ∪ t).restrict f) '' ((inclusion (subset_union_left s t)) '' univ) :=
begin
ext,
simp only [mem_image, restrict_apply, mem_univ, true_and, set_coe.exists, inclusion_mk,
mem_union, subtype.mk_eq_mk, exists_prop, exists_eq_right, subtype.coe_mk],
exact ⟨Exists.imp (λ a, by tauto), Exists.imp (λ a, by tauto)⟩,
end
lemma restrict_image_union_right {α β} (s t : set α) (f : α → β) :
f '' t = ((s ∪ t).restrict f) '' ((inclusion (subset_union_right s t)) '' univ) :=
begin
ext,
simp only [mem_image, restrict_apply, mem_univ, true_and, set_coe.exists, inclusion_mk,
mem_union, subtype.mk_eq_mk, exists_prop, exists_eq_right, subtype.coe_mk],
exact ⟨Exists.imp (λ a, by tauto), Exists.imp (λ a, by tauto)⟩,
end
end set
variables {F V ι : Type*} [field F] [add_comm_group V] [module F V]
open submodule set
lemma linear_independent.subfamily {I J : set ι} (hJI : J ⊆ I) {v : ι → V}
(hI : linear_independent F (I.restrict v)) : linear_independent F (J.restrict v) :=
begin
rw (show J.restrict v = (I.restrict v) ∘ (inclusion hJI), from by {ext, simp}),
exact linear_independent.comp hI _ (inclusion_injective hJI),
end
lemma linear_independent.quotient₁ {I J : set ι} (hIJ : disjoint I J) {v : ι → V}
(hv : linear_independent F ((I ∪ J).restrict v)) :
linear_independent F (J.restrict ((mkq (span F (v '' I))) ∘ v)) :=
begin
rw (show J.restrict (mkq (span F (v '' I)) ∘ v) = mkq (span F (v '' I)) ∘ (J.restrict v),
from by {ext, simp}),
refine linear_independent.map (linear_independent.subfamily (subset_union_right I J) hv) _,
simp only [range_restrict, ker_mkq, restrict_image_union_left I J v,
restrict_image_union_right I J v],
refine linear_independent.disjoint_span_image hv (set.disjoint_iff.mpr (λ i hi, _)),
simp only [mem_inter_iff, mem_image, mem_univ, true_and, set_coe.exists, inclusion_mk] at hi,
obtain ⟨⟨x₁, hx₁J, hx₁⟩, ⟨x₂, hx₂I, hx₂⟩⟩ := hi,
rw [← hx₁, subtype.mk_eq_mk] at hx₂,
exact disjoint.ne_of_mem hIJ hx₂I hx₁J hx₂,
end
But I'm not exactly happy with it (in particular with the need for the set
lemmas). Can this be improved?
Anne Baanen (Mar 29 2023 at 09:48):
I think this should be doable with docs#linear_independent.map and docs#linear_independent.disjoint_span_image, but the last one requires linear_independent F v
instead of linear_independent F ((I ∪ J).restrict v)
. Let me see if I can weaken the hypothesis sufficiently...
Anne Baanen (Mar 29 2023 at 10:01):
import linear_algebra.linear_independent
import linear_algebra.quotient
variables {F V ι : Type*} [field F] [add_comm_group V] [module F V]
open submodule set
lemma linear_independent.subfamily {I J : set ι} (hJI : J ⊆ I) {v : ι → V}
(hI : linear_independent F (I.restrict v)) : linear_independent F (J.restrict v) :=
begin
rw (show J.restrict v = (I.restrict v) ∘ (inclusion hJI), from by {ext, simp}),
exact linear_independent.comp hI _ (inclusion_injective hJI),
end
lemma linear_independent.disjoint_span_image' {ι R M : Type*} {v : ι → M} {I J : set ι}
[ring R] [add_comm_group M] [module R M] (hv : linear_independent R ((I ∪ J).restrict v)) (hs : disjoint I J) :
disjoint (submodule.span R (v '' I)) (submodule.span R (v '' J)) :=
begin
set I' : set (coe_sort (I ∪ J)) := (coe ⁻¹' I) with I'_def,
set J' : set (coe_sort (I ∪ J)) := (coe ⁻¹' J) with J'_def,
have : disjoint I' J',
{ rw [set.disjoint_iff, I'_def, J'_def] at *,
rintros ⟨x, (hxI | hxJ)⟩ hx;
exact hs hx },
convert linear_independent.disjoint_span_image hv this using 2,
{ ext, rw [I'_def, set.image_restrict, set.inter_comm, set.union_inter_cancel_left] },
{ ext, rw [J'_def, set.image_restrict, set.inter_comm, set.union_inter_cancel_right] }
end
lemma linear_independent.quotient₁ {I J : set ι} (hIJ : disjoint I J) {v : ι → V}
(hv : linear_independent F ((I ∪ J).restrict v)) :
linear_independent F (J.restrict ((mkq (span F (v '' I))) ∘ v)) :=
begin
refine linear_independent.map (linear_independent.subfamily (set.subset_union_right I J) hv) _,
rw [submodule.ker_mkq],
convert (linear_independent.disjoint_span_image' hv hIJ).symm,
ext,
simp
end
Michael Stoll (Mar 29 2023 at 21:37):
Thanks; that looks a bit better (even though it is built from the same building blocks).
Michael Stoll (Apr 03 2023 at 10:27):
Next level: After defining
variables (R : Type*) {M ι : Type*} [semiring R] [add_comm_monoid M] [module R M]
def linear_independent_on (v : ι → M) (s : set ι) : Prop := linear_independent R (s.restrict v)
I want to show
variables {R M ι : Type*} [ring R] [add_comm_group M] [module R M]
lemma linear_independent_on.union {s t : set ι} {v : ι → M} (hs : linear_independent_on R v s)
(ht : linear_independent_on R v t)
(h : disjoint (submodule.span R (v '' s)) (submodule.span R (v '' t))) :
linear_independent_on R v (s ∪ t) := sorry
I have come up with the following proof, which needs some extra stuff connected to sets and sum types.
import linear_algebra.linear_independent
import linear_algebra.quotient
namespace set
def union_to_sum {α} (s t : set α) [decidable_pred (λ x, x ∈ s)] : (s ∪ t) → sum s t :=
λ x, if hx : x.val ∈ s then sum.inl ⟨x.val, hx⟩
else sum.inr ⟨x.val, x.property.resolve_left hx⟩
lemma union_to_sum_inj {α} (s t : set α) [decidable_pred (λ x, x ∈ s)] :
function.injective (union_to_sum s t) :=
begin
intros x y hf,
simp only [union_to_sum, subtype.val_eq_coe] at hf,
by_cases hx : ↑x ∈ s; by_cases hy : ↑y ∈ s;
simp only [hx, hy, not_false_iff, dif_neg, dif_pos, subtype.mk_eq_mk] at hf,
{ exact subtype.ext hf, },
{ exact false.elim hf, },
{ exact false.elim hf, },
{ exact subtype.ext hf, }
end
end set
section linear_indep
variables {R M ι : Type*} [ring R] [add_comm_group M] [module R M]
variables (R)
def linear_independent_on (v : ι → M) (s : set ι) : Prop := linear_independent R (s.restrict v)
variables {R}
open set submodule
lemma linear_independent_on.union {s t : set ι} {v : ι → M} (hs : linear_independent_on R v s)
(ht : linear_independent_on R v t)
(h : disjoint (submodule.span R (v '' s)) (submodule.span R (v '' t))) :
linear_independent_on R v (s ∪ t) :=
begin
simp_rw ← range_restrict at h,
dsimp [linear_independent_on],
classical,
convert linear_independent.comp (linear_independent.sum_type hs ht h)
(union_to_sum s t) (union_to_sum_inj s t),
{ ext x,
simp only [union_to_sum, subtype.val_eq_coe, restrict_apply, function.comp_app],
split_ifs with hx hx,
{ simp only [sum.elim_inl, restrict_apply, subtype.coe_mk], },
{ simp only [sum.elim_inr, restrict_apply, subtype.coe_mk], } },
end
end linear_indep
and I'm wondering again whether there might be a simpler way.
Michael Stoll (Apr 09 2023 at 19:27):
I need the fact that a family f : ι → M
is linearly independent if and only if s.card ≤ finrank R (span R (s.image f : set M))
for all s : finset ι
(where M
is a vector space over R
), but I can't find it in mathlib.
There is docs#linear_independent_iff_card_le_finrank_span, which is sort of half of what I need, but there does not seem to be an obvious way to connect this easily with linear independence on an arbitrary type. What I have come up with so far is the following.
import tactic
import algebra.module.basic
import linear_algebra.finrank
import linear_algebra.finite_dimensional
namespace linear_independent
open finite_dimensional submodule
variables (R : Type*) [division_ring R]
variables (M : Type*) [add_comm_group M] [decidable_eq M] [module R M]
variables {ι : Type*} [decidable_eq ι]
lemma iff_card_le_rank_span_on_finsets (f : ι → M) :
linear_independent R f ↔ ∀ s : finset ι, s.card ≤ finrank R (span R (s.image f : set M)) :=
begin
have h : ∀ s : finset ι, (finset.image f s : set M) = set.range (f ∘ (coe : s → ι)),
{ intro s,
ext,
simp only [finset.coe_image, set.mem_image, finset.mem_coe, set.mem_range,
function.comp_app, finset.exists_coe, subtype.coe_mk, exists_prop], },
refine ⟨λ H s, _, λ H, _⟩,
{ have H₁ := comp H (coe : s → ι) subtype.coe_injective,
convert linear_independent_iff_card_le_finrank_span.mp H₁ using 1,
{ exact (fintype.card_coe s).symm, },
{ simp only [set.finrank],
rw h, } },
{ rw linear_independent_iff',
refine λ s g hg i hi, _,
rw ← finset.sum_finset_coe at hg,
specialize H s,
rw [← fintype.card_coe, h] at H,
replace H := fintype.linear_independent_iff.mp
(linear_independent_iff_card_le_finrank_span.mpr H) (g ∘ coe) hg ⟨i, hi⟩,
exact H, }
end
Is there a better way?
(BTW, exact fintype.linear_independent_iff.mp ...
does not work; it wants a fintype ι
instance...)
Last updated: Dec 20 2023 at 11:08 UTC