Zulip Chat Archive

Stream: Is there code for X?

Topic: Product of i < j and j < i


Riccardo Brasca (Nov 05 2021 at 13:42):

This was nonsense.
Does someone see a quick way of proving the following?

Alex J. Best (Nov 05 2021 at 13:49):

Is this true as stated? Why can't the set of i larger than a be empty say and the other one not be?

Riccardo Brasca (Nov 05 2021 at 13:50):

Because I am stupid.

Riccardo Brasca (Nov 05 2021 at 13:50):

Time for coffee

Riccardo Brasca (Nov 05 2021 at 14:21):

Ok, the real question is

import data.fin.interval

open_locale big_operators

example {R : Type*} [comm_ring R] {n : } (f : fin n  R) :
   i, ( j in finset.univ.filter (λ j, j < i), (f j - f i) * (f i - f j)) =
   i, ( j in finset.univ.filter (λ j, i  j), (f j - f i)) := sorry

I am not asking to do my work, but suggestions are welcome :)

Eric Wieser (Nov 05 2021 at 14:24):

I think the RHS is ∏ i in (finset.univ : finset ℕ).off_diag, f i.2 - f i.1?

Yaël Dillies (Nov 05 2021 at 14:27):

You can move multiplication out of the LHS, swap the products on the right factor, then split the prod on the RHS as the i < j and j < i bits.

Eric Wieser (Nov 05 2021 at 14:29):

Do we have something like docs#finset.filter_or

Riccardo Brasca (Nov 05 2021 at 14:29):

It's the "swap the product" part that is causing me troubles.

Riccardo Brasca (Nov 05 2021 at 14:30):

Ah, docs#finset.filter_or seems relevant

Eric Wieser (Nov 05 2021 at 14:35):

Yeah, simp_rw [ne_iff_lt_or_gt, finset.filter_or], is a good start

Yaël Dillies (Nov 05 2021 at 14:36):

You might need to turn the double sum in a single one using docs#finset.product and docs#finset.prod_product.

Yaël Dillies (Nov 05 2021 at 14:37):

And once again Eric, finset.prod_product_right would come in handy!

Eric Wieser (Nov 05 2021 at 14:39):

Well, no more handy than rw [prod_product, prod_comm]

Eric Wieser (Nov 05 2021 at 14:48):

This gets through some of the pain:

example {R : Type*} [comm_ring R] {n : } (f : fin n  R) :
   i, ( j in finset.univ.filter (λ j, j < i), (f j - f i) * (f i - f j)) =
   i, ( j in finset.univ.filter (λ j, i  j), (f j - f i)) :=
begin
  simp_rw [ne_iff_lt_or_gt, finset.filter_or],
  refine eq.trans _ (congr_arg (finset.prod _) (funext $ λ i, (finset.prod_union _).symm)),
  simp_rw [finset.prod_mul_distrib],
  sorry,
  { rintro x hx,
    obtain ⟨⟨_, hl⟩, _, hg⟩⟩ := (finset.mem_inter.1 hx).imp finset.mem_filter.1 finset.mem_filter.1,
    exact (lt_asymm hl hg).elim, },
end

Riccardo Brasca (Nov 05 2021 at 15:48):

example {R : Type*} [comm_ring R] {n : } (f : fin n  R) :
   i, ( j in finset.univ.filter (λ j, j < i), (f j - f i) * (f i - f j)) =
   i, ( j in finset.univ.filter (λ j, i  j), (f j - f i)) :=
begin
  simp_rw [ne_iff_lt_or_gt, finset.filter_or],
  refine eq.trans _ (congr_arg (finset.prod _) (funext $ λ i, (finset.prod_union _).symm)),
  simp_rw [finset.prod_mul_distrib],
  { conv_rhs {
      congr, skip, congr, skip, funext,
      conv {
        congr, skip, funext,
        rw [ neg_sub, neg_eq_neg_one_mul] },
        rw [finset.prod_mul_distrib, finset.prod_const], },
    simp_rw [finset.prod_mul_distrib],
    rw [ mul_assoc],
    congr,
    sorry,
  },
  { rintro x hx,
    obtain ⟨⟨_, hl⟩, _, hg⟩⟩ := (finset.mem_inter.1 hx).imp finset.mem_filter.1 finset.mem_filter.1,
    exact (lt_asymm hl hg).elim, },
end

Takes care of one half of the product, the easy part...

Riccardo Brasca (Nov 05 2021 at 16:34):

And let's simp for the win.

lemma prod_filter_lt_mul_neg_eq_prod_off_diag {R : Type*} [comm_ring R] {n : } (f : fin n  R) :
   i, ( j in finset.univ.filter (λ j, j < i), (f j - f i) * (f i - f j)) =
   i, ( j in finset.univ.filter (λ j, i  j), (f j - f i)) :=
begin
  simp_rw [ne_iff_lt_or_gt, finset.filter_or],
  refine eq.trans _ (congr_arg (finset.prod _) (funext $ λ i, (finset.prod_union _).symm)),
  simp_rw [finset.prod_mul_distrib],
  { conv_rhs {
      congr, skip, congr, skip, funext,
      conv {
        congr, skip, funext,
        rw [ neg_sub, neg_eq_neg_one_mul] },
      rw [finset.prod_mul_distrib, finset.prod_const] },
    simp_rw [finset.prod_mul_distrib],
    rw [ mul_assoc],
    congr,
    conv_lhs {
      congr, skip, funext,
      conv {
        congr, skip, funext,
        rw [ neg_sub, neg_eq_neg_one_mul] },
      rw [finset.prod_mul_distrib, finset.prod_const] },
    simp_rw [finset.prod_mul_distrib, filter_gt_card],
    nth_rewrite 0 [mul_comm],
    congr' 1,
    rw [finset.prod_sigma', finset.prod_sigma'],
    exact finset.prod_bij' (λ i hi, i.2, i.1⟩) (by simp) (by simp) (λ i hi, i.2, i.1⟩)
      (by simp) (by simp) (by simp) },
  { rintro x hx,
    obtain ⟨⟨_, hl⟩, _, hg⟩⟩ := (finset.mem_inter.1 hx).imp finset.mem_filter.1 finset.mem_filter.1,
    exact (lt_asymm hl hg).elim, },
end

Eric Wieser (Nov 05 2021 at 16:53):

Does this lemma generalize to g i j = f i - f j?

Floris van Doorn (Nov 05 2021 at 17:11):

Probably, as long as g i j = - g j i.

Floris van Doorn (Nov 05 2021 at 17:12):

Oh, or maybe that condition is not even needed

Floris van Doorn (Nov 05 2021 at 17:14):

It can probably be further generalized by replacing ...
edit: nevermind

Riccardo Brasca (Nov 05 2021 at 17:16):

Yes, it should be generalized and golfed


Last updated: Dec 20 2023 at 11:08 UTC