Built with doc-gen4, running Lean4. Bubbles () indicate interactive fragments: hover for details, tap to reveal contents. Use Ctrl+↑Ctrl+↓to navigate, Ctrl+πŸ–±οΈto focus. On Mac, use Cmdinstead of Ctrl.
import Mathlib.Algebra.GroupPower.Lemmas
import Mathlib.Algebra.Group.Prod
import Mathlib.Data.Int.Cast.Lemmas
import Mathlib.Algebra.Ring.Basic
import UnitConjecture.EnumDecide

/-!

## Free groups

The definition of a free group on a basis, along with a few properties.

Free groups are defined constructively to allow automatic equality checking of 
homomorphisms on finitely generated free groups.

## Overview
- `AddFreeGroup` - the main definition.
- `decideHomsEqual` - the crucial result that allows the 
  automatic comparison of homomorphisms by checking their values on the basis.
- `β„€Free` - a proof that the additive group of integers is a free group on the one-element type.
- `prodFree` - a proof that the product of free groups is free.
-/

/-- Free (Additive) Groups, implemented as a typeclass.
    A free additive group with a basis `X` is an additive group `F` with an inclusion map `ΞΉ : X β†’ F`,
    such that any map `f : X β†’ A` from the basis to any Abelian group `A`
    extends *uniquely* to an *additive group homomorphism* `Ο† : F β†’+ A`. -/
class 
AddFreeGroup: {F : Type u_1} β†’ [inst : AddCommGroup F] β†’ {X : Type u_2} β†’ (ΞΉ : X β†’ F) β†’ (inducedHom : (A : Type) β†’ [inst_1 : AddCommGroup A] β†’ (X β†’ A) β†’ F β†’+ A) β†’ (βˆ€ {A : Type} [inst_1 : AddCommGroup A] (f : X β†’ A), ↑(inducedHom A f) ∘ ΞΉ = f) β†’ (βˆ€ {A : Type} [inst_1 : AddCommGroup A] (f g : F β†’+ A), ↑f ∘ ΞΉ = ↑g ∘ ΞΉ β†’ f = g) β†’ AddFreeGroup F X
AddFreeGroup
(
F: Type ?u.2
F
:
Type _: Type (?u.2+1)
Type _
) [
AddCommGroup: Type ?u.5 β†’ Type ?u.5
AddCommGroup
F: Type ?u.2
F
] (
X: Type ?u.8
X
:
Type _: Type (?u.8+1)
Type _
) where /-- The inclusion map from the basis to the free group. -/
ΞΉ: {F : Type u_1} β†’ [inst : AddCommGroup F] β†’ {X : Type u_2} β†’ [self : AddFreeGroup F X] β†’ X β†’ F
ΞΉ
:
X: Type ?u.8
X
β†’
F: Type ?u.2
F
/-- The homomorphism from the free group induced by a map from the basis. -/
inducedHom: {F : Type u_1} β†’ [inst : AddCommGroup F] β†’ {X : Type u_2} β†’ [self : AddFreeGroup F X] β†’ (A : Type) β†’ [inst_1 : AddCommGroup A] β†’ (X β†’ A) β†’ F β†’+ A
inducedHom
: (
A: Type
A
:
Type: Type 1
Type
) β†’ [
AddCommGroup: Type ?u.21 β†’ Type ?u.21
AddCommGroup
A: Type
A
] β†’ (
X: Type ?u.8
X
β†’
A: Type
A
) β†’ (
F: Type ?u.2
F
β†’+
A: Type
A
) /-- A proof that the induced homomorphism extends the map from the basis. -/
induced_extends: βˆ€ {F : Type u_1} [inst : AddCommGroup F] {X : Type u_2} [self : AddFreeGroup F X] {A : Type} [inst_1 : AddCommGroup A] (f : X β†’ A), ↑(AddFreeGroup.inducedHom A f) ∘ AddFreeGroup.ΞΉ = f
induced_extends
{
A: Type
A
:
Type: Type 1
Type
} [
AddCommGroup: Type ?u.464 β†’ Type ?u.464
AddCommGroup
A: Type
A
] : βˆ€
f: X β†’ A
f
:
X: Type ?u.8
X
β†’
A: Type
A
, (
inducedHom: (A : Type) β†’ [inst : AddCommGroup A] β†’ (X β†’ A) β†’ F β†’+ A
inducedHom
A: Type
A
f: X β†’ A
f
) ∘
ΞΉ: X β†’ F
ΞΉ
=
f: X β†’ A
f
/-- A proof that any homomorphism extending a map from the basis must be unique. -/
unique_extension: βˆ€ {F : Type u_1} [inst : AddCommGroup F] {X : Type u_2} [self : AddFreeGroup F X] {A : Type} [inst_1 : AddCommGroup A] (f g : F β†’+ A), ↑f ∘ AddFreeGroup.ΞΉ = ↑g ∘ AddFreeGroup.ΞΉ β†’ f = g
unique_extension
{
A: Type
A
:
Type: Type 1
Type
} [
AddCommGroup: Type ?u.1275 β†’ Type ?u.1275
AddCommGroup
A: Type
A
] (
f: F β†’+ A
f
g: F β†’+ A
g
:
F: Type ?u.2
F
β†’+
A: Type
A
) :
f: F β†’+ A
f
∘
ΞΉ: X β†’ F
ΞΉ
=
g: F β†’+ A
g
∘
ΞΉ: X β†’ F
ΞΉ
β†’
f: F β†’+ A
f
=
g: F β†’+ A
g
/-- The additive group of integers `β„€` is the free group on a singleton basis. -/ instance β„€Free :
AddFreeGroup: (F : Type ?u.3359) β†’ [inst : AddCommGroup F] β†’ Type ?u.3358 β†’ Type (max(max1?u.3359)?u.3358)
AddFreeGroup
β„€: Type
β„€
Unit: Type
Unit
where ΞΉ := fun
_: ?m.3377
_
=>
1: ?m.3380
1
inducedHom := fun
A: ?m.3393
A
_: ?m.3396
_
f: ?m.3399
f
=> (
zmultiplesHom: (A : Type ?u.3402) β†’ [inst : AddGroup A] β†’ A ≃ (β„€ β†’+ A)
zmultiplesHom
A: ?m.3393
A
).
toFun: {Ξ± : Sort ?u.3485} β†’ {Ξ² : Sort ?u.3484} β†’ Ξ± ≃ Ξ² β†’ Ξ± β†’ Ξ²
toFun
(
f: ?m.3399
f
(): Unit
()
) induced_extends :=

βˆ€ {A : Type} [inst : AddCommGroup A] (f : Unit β†’ A), (↑((fun A x f => Equiv.toFun (zmultiplesHom A) (f ())) A inst f) ∘ fun x => 1) = f
A: Type

inst✝: AddCommGroup A

f: Unit β†’ A


(↑((fun A x f => Equiv.toFun (zmultiplesHom A) (f ())) A inst✝ f) ∘ fun x => 1) = f

βˆ€ {A : Type} [inst : AddCommGroup A] (f : Unit β†’ A), (↑((fun A x f => Equiv.toFun (zmultiplesHom A) (f ())) A inst f) ∘ fun x => 1) = f
A: Type

inst✝: AddCommGroup A

f: Unit β†’ A

u: Unit


h
Function.comp (↑((fun A x f => Equiv.toFun (zmultiplesHom A) (f ())) A inst✝ f)) (fun x => 1) u = f u
A: Type

inst✝: AddCommGroup A

f: Unit β†’ A

u: Unit


h
Function.comp (↑((fun A x f => Equiv.toFun (zmultiplesHom A) (f ())) A inst✝ f)) (fun x => 1) u = f u

βˆ€ {A : Type} [inst : AddCommGroup A] (f : Unit β†’ A), (↑((fun A x f => Equiv.toFun (zmultiplesHom A) (f ())) A inst f) ∘ fun x => 1) = f
A: Type

inst✝: AddCommGroup A

f: Unit β†’ A


h.unit
Function.comp (↑((fun A x f => Equiv.toFun (zmultiplesHom A) (f ())) A inst✝ f)) (fun x => 1) PUnit.unit = f PUnit.unit

βˆ€ {A : Type} [inst : AddCommGroup A] (f : Unit β†’ A), (↑((fun A x f => Equiv.toFun (zmultiplesHom A) (f ())) A inst f) ∘ fun x => 1) = f

Goals accomplished! πŸ™
unique_extension :=

βˆ€ {A : Type} [inst : AddCommGroup A] (f g : β„€ β†’+ A), ((↑f ∘ fun x => 1) = ↑g ∘ fun x => 1) β†’ f = g
A: Type

abg: AddCommGroup A

f, g: β„€ β†’+ A

hyp: (↑f ∘ fun x => 1) = ↑g ∘ fun x => 1


f = g

βˆ€ {A : Type} [inst : AddCommGroup A] (f g : β„€ β†’+ A), ((↑f ∘ fun x => 1) = ↑g ∘ fun x => 1) β†’ f = g
A: Type

abg: AddCommGroup A

f, g: β„€ β†’+ A

hyp: (↑f ∘ fun x => 1) = ↑g ∘ fun x => 1

hyp':= congrFun hyp (): Function.comp (↑f) (fun x => 1) () = Function.comp (↑g) (fun x => 1) ()


f = g

βˆ€ {A : Type} [inst : AddCommGroup A] (f g : β„€ β†’+ A), ((↑f ∘ fun x => 1) = ↑g ∘ fun x => 1) β†’ f = g
A: Type

abg: AddCommGroup A

f, g: β„€ β†’+ A

hyp: (↑f ∘ fun x => 1) = ↑g ∘ fun x => 1

hyp':= congrFun hyp (): ↑f 1 = ↑g 1


f = g

βˆ€ {A : Type} [inst : AddCommGroup A] (f g : β„€ β†’+ A), ((↑f ∘ fun x => 1) = ↑g ∘ fun x => 1) β†’ f = g
A: Type

abg: AddCommGroup A

f, g: β„€ β†’+ A

hyp: (↑f ∘ fun x => 1) = ↑g ∘ fun x => 1

hyp':= congrFun hyp (): ↑f 1 = ↑g 1


f = g
A: Type

abg: AddCommGroup A

f, g: β„€ β†’+ A

hyp: (↑f ∘ fun x => 1) = ↑g ∘ fun x => 1

hyp': ↑(Equiv.symm (zmultiplesHom A)) f = ↑g 1


f = g
A: Type

abg: AddCommGroup A

f, g: β„€ β†’+ A

hyp: (↑f ∘ fun x => 1) = ↑g ∘ fun x => 1

hyp':= congrFun hyp (): ↑f 1 = ↑g 1


f = g
A: Type

abg: AddCommGroup A

f, g: β„€ β†’+ A

hyp: (↑f ∘ fun x => 1) = ↑g ∘ fun x => 1

hyp': ↑(Equiv.symm (zmultiplesHom A)) f = ↑(Equiv.symm (zmultiplesHom A)) g


f = g
A: Type

abg: AddCommGroup A

f, g: β„€ β†’+ A

hyp: (↑f ∘ fun x => 1) = ↑g ∘ fun x => 1

hyp':= congrFun hyp (): ↑f 1 = ↑g 1


f = g
A: Type

abg: AddCommGroup A

f, g: β„€ β†’+ A

hyp: (↑f ∘ fun x => 1) = ↑g ∘ fun x => 1

hyp': f = g


f = g
A: Type

abg: AddCommGroup A

f, g: β„€ β†’+ A

hyp: (↑f ∘ fun x => 1) = ↑g ∘ fun x => 1

hyp': f = g


f = g

Goals accomplished! πŸ™
open EnumDecide in /-- Equality of homomorphisms from a free group on an exhaustively searchable basis is decidable. -/ @[instance] def
decideHomsEqual: {F : Type ?u.6984} β†’ [inst : AddCommGroup F] β†’ {X : Type ?u.6990} β†’ [inst_1 : DecideForall X] β†’ [fgp : AddFreeGroup F X] β†’ {A : Type ?u.7008} β†’ [inst_2 : AddCommGroup A] β†’ [inst_3 : DecidableEq A] β†’ DecidableEq (F β†’+ A)
decideHomsEqual
{
F: Type ?u.6984
F
:
Type _: Type (?u.6984+1)
Type _
} [
AddCommGroup: Type ?u.6987 β†’ Type ?u.6987
AddCommGroup
F: Type ?u.6984
F
] {
X: Type ?u.6990
X
:
Type _: Type (?u.6990+1)
Type _
} [
DecideForall: Type ?u.6993 β†’ Type ?u.6993
DecideForall
X: Type ?u.6990
X
] [
fgp: AddFreeGroup F X
fgp
:
AddFreeGroup: (F : Type ?u.6997) β†’ [inst : AddCommGroup F] β†’ Type ?u.6996 β†’ Type (max(max1?u.6997)?u.6996)
AddFreeGroup
F: Type ?u.6984
F
X: Type ?u.6990
X
] {
A: Type ?u.7008
A
:
Type _: Type (?u.7008+1)
Type _
} [
AddCommGroup: Type ?u.7011 β†’ Type ?u.7011
AddCommGroup
A: Type ?u.7008
A
] [
DecidableEq: Sort ?u.7014 β†’ Sort (max1?u.7014)
DecidableEq
A: Type ?u.7008
A
] :
DecidableEq: Sort ?u.7023 β†’ Sort (max1?u.7023)
DecidableEq
(
F: Type ?u.6984
F
β†’+
A: Type ?u.7008
A
) := fun
f: ?m.7478
f
g: ?m.7481
g
=> if
c: ?m.9157
c
: βˆ€
x: X
x
:
X: Type ?u.6990
X
,
f: ?m.7478
f
(
fgp: AddFreeGroup F X
fgp
.
ΞΉ: {F : Type ?u.8274} β†’ [inst : AddCommGroup F] β†’ {X : Type ?u.8273} β†’ [self : AddFreeGroup F X] β†’ X β†’ F
ΞΉ
x: X
x
) =
g: ?m.7481
g
(
fgp: AddFreeGroup F X
fgp
.
ΞΉ: {F : Type ?u.9052} β†’ [inst : AddCommGroup F] β†’ {X : Type ?u.9051} β†’ [self : AddFreeGroup F X] β†’ X β†’ F
ΞΉ
x: X
x
) then
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type ?u.7008

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)


Decidable (f = g)
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type ?u.7008

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)


h
f = g
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type ?u.7008

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)


Decidable (f = g)
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)


h.a
↑f ∘ AddFreeGroup.ΞΉ = ↑g ∘ AddFreeGroup.ΞΉ
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type ?u.7008

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)


Decidable (f = g)
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)

x: X


h.a.h
Function.comp (↑f) AddFreeGroup.ΞΉ x = Function.comp (↑g) AddFreeGroup.ΞΉ x
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type ?u.7008

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)


Decidable (f = g)

Goals accomplished! πŸ™
else
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: Β¬βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)


Decidable (f = g)
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: Β¬βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)


h
Β¬f = g
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: Β¬βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)


Decidable (f = g)
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: Β¬βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)

contra: f = g


h
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: Β¬βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)


Decidable (f = g)
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: Β¬βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)

contra: f = g


h
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: Β¬βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)

contra: f = g


βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: Β¬βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)

contra: f = g

x✝: X


↑f (AddFreeGroup.ΞΉ x✝) = ↑g (AddFreeGroup.ΞΉ x✝)
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: Β¬βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)

contra: f = g

x✝: X


↑f (AddFreeGroup.ΞΉ x✝) = ↑g (AddFreeGroup.ΞΉ x✝)
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: Β¬βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)

contra: f = g


βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)

Goals accomplished! πŸ™
F: Type ?u.6984

inst✝³: AddCommGroup F

X: Type ?u.6990

inst✝²: DecideForall X

fgp: AddFreeGroup F X

A: Type

inst✝¹: AddCommGroup A

inst✝: DecidableEq A

f, g: F β†’+ A

c: Β¬βˆ€ (x : X), ↑f (AddFreeGroup.ΞΉ x) = ↑g (AddFreeGroup.ΞΉ x)


Decidable (f = g)

Goals accomplished! πŸ™
namespace AddFreeGroup.Product variable {
A: Type ?u.14585
A
B: Type ?u.11319
B
:
Type _: Type (?u.12604+1)
Type _
} [
AddCommGroup: Type ?u.11322 β†’ Type ?u.11322
AddCommGroup
A: Type ?u.11328
A
] [
AddCommGroup: Type ?u.11355 β†’ Type ?u.11355
AddCommGroup
B: Type ?u.14588
B
] variable {
X_A: Type ?u.11358
X_A
X_B: Type ?u.14600
X_B
:
Type _: Type (?u.11358+1)
Type _
} variable [
FAb_A: AddFreeGroup A X_A
FAb_A
:
AddFreeGroup: (F : Type ?u.11365) β†’ [inst : AddCommGroup F] β†’ Type ?u.11364 β†’ Type (max(max1?u.11365)?u.11364)
AddFreeGroup
A: Type ?u.11346
A
X_A: Type ?u.11358
X_A
] [
FAb_B: AddFreeGroup B X_B
FAb_B
:
AddFreeGroup: (F : Type ?u.11377) β†’ [inst : AddCommGroup F] β†’ Type ?u.11376 β†’ Type (max(max1?u.11377)?u.11376)
AddFreeGroup
B: Type ?u.12604
B
X_B: Type ?u.11361
X_B
] /-- The inclusion map from the direct sum of the bases of two free groups into their product. -/ def
ΞΉ: X_A βŠ• X_B β†’ A Γ— B
ΞΉ
: (
X_A: Type ?u.11400
X_A
βŠ•
X_B: Type ?u.11403
X_B
) β†’
A: Type ?u.11388
A
Γ—
B: Type ?u.11391
B
|
Sum.inl: {Ξ± : Type ?u.11441} β†’ {Ξ² : Type ?u.11440} β†’ Ξ± β†’ Ξ± βŠ• Ξ²
Sum.inl
x_a: X_A
x_a
=> (
FAb_A: AddFreeGroup A X_A
FAb_A
.
ΞΉ: {F : Type ?u.11467} β†’ [inst : AddCommGroup F] β†’ {X : Type ?u.11466} β†’ [self : AddFreeGroup F X] β†’ X β†’ F
ΞΉ
x_a: X_A
x_a
,
0: ?m.11482
0
) |
Sum.inr: {Ξ± : Type ?u.11833} β†’ {Ξ² : Type ?u.11832} β†’ Ξ² β†’ Ξ± βŠ• Ξ²
Sum.inr
x_b: X_B
x_b
=> (
0: ?m.11855
0
,
FAb_B: AddFreeGroup B X_B
FAb_B
.
ΞΉ: {F : Type ?u.12204} β†’ [inst : AddCommGroup F] β†’ {X : Type ?u.12203} β†’ [self : AddFreeGroup F X] β†’ X β†’ F
ΞΉ
x_b: X_B
x_b
) /-- The group homomorphism from the product of two free groups induced by a map from the basis. -/ def
inducedProdHom: (G : Type ?u.12643) β†’ [inst : AddCommGroup G] β†’ (X_A βŠ• X_B β†’ G) β†’ A Γ— B β†’+ G
inducedProdHom
(
G: Type ?u.12643
G
:
Type _: Type (?u.12643+1)
Type _
) [
AddCommGroup: Type ?u.12646 β†’ Type ?u.12646
AddCommGroup
G: Type ?u.12643
G
] (
f: X_A βŠ• X_B β†’ G
f
:
X_A: Type ?u.12613
X_A
βŠ•
X_B: Type ?u.12616
X_B
β†’
G: Type ?u.12643
G
) :
A: Type ?u.12601
A
Γ—
B: Type ?u.12604
B
β†’+
G: Type ?u.12643
G
:= let
f_A: X_A β†’ G
f_A
:
X_A: Type ?u.12613
X_A
β†’
G: Type ?u.12643
G
:=
f: X_A βŠ• X_B β†’ G
f
∘
Sum.inl: {Ξ± : Type ?u.13332} β†’ {Ξ² : Type ?u.13331} β†’ Ξ± β†’ Ξ± βŠ• Ξ²
Sum.inl
let
f_B: X_B β†’ G
f_B
:
X_B: Type ?u.12616
X_B
β†’
G: Type ?u.12643
G
:=
f: X_A βŠ• X_B β†’ G
f
∘
Sum.inr: {Ξ± : Type ?u.13359} β†’ {Ξ² : Type ?u.13358} β†’ Ξ² β†’ Ξ± βŠ• Ξ²
Sum.inr
AddMonoidHom.coprod: {M : Type ?u.13371} β†’ {N : Type ?u.13370} β†’ {P : Type ?u.13369} β†’ [inst : AddZeroClass M] β†’ [inst_1 : AddZeroClass N] β†’ [inst_2 : AddCommMonoid P] β†’ (M β†’+ P) β†’ (N β†’+ P) β†’ M Γ— N β†’+ P
AddMonoidHom.coprod
(
FAb_A: AddFreeGroup A X_A
FAb_A
.
inducedHom: {F : Type ?u.13712} β†’ [inst : AddCommGroup F] β†’ {X : Type ?u.13711} β†’ [self : AddFreeGroup F X] β†’ (A : Type) β†’ [inst_1 : AddCommGroup A] β†’ (X β†’ A) β†’ F β†’+ A
inducedHom
G: Type ?u.12643
G
f_A: X_A β†’ G
f_A
) (
FAb_B: AddFreeGroup B X_B
FAb_B
.
inducedHom: {F : Type ?u.13762} β†’ [inst : AddCommGroup F] β†’ {X : Type ?u.13761} β†’ [self : AddFreeGroup F X] β†’ (A : Type) β†’ [inst_1 : AddCommGroup A] β†’ (X β†’ A) β†’ F β†’+ A
inducedHom
G: Type ?u.12643
G
f_B: X_B β†’ G
f_B
) /-- The product of free groups is free. -/ instance
prodFree: AddFreeGroup (A Γ— B) (X_A βŠ• X_B)
prodFree
:
AddFreeGroup: (F : Type ?u.14628) β†’ [inst : AddCommGroup F] β†’ Type ?u.14627 β†’ Type (max(max1?u.14628)?u.14627)
AddFreeGroup
(
A: Type ?u.14585
A
Γ—
B: Type ?u.14588
B
) (
X_A: Type ?u.14597
X_A
βŠ•
X_B: Type ?u.14600
X_B
) := { ΞΉ :=
ΞΉ: {A : Type ?u.14696} β†’ {B : Type ?u.14695} β†’ [inst : AddCommGroup A] β†’ [inst_1 : AddCommGroup B] β†’ {X_A : Type ?u.14694} β†’ {X_B : Type ?u.14693} β†’ [FAb_A : AddFreeGroup A X_A] β†’ [FAb_B : AddFreeGroup B X_B] β†’ X_A βŠ• X_B β†’ A Γ— B
ΞΉ
inducedHom :=
inducedProdHom: {A : Type ?u.14775} β†’ {B : Type ?u.14774} β†’ [inst : AddCommGroup A] β†’ [inst_1 : AddCommGroup B] β†’ {X_A : Type ?u.14773} β†’ {X_B : Type ?u.14772} β†’ [FAb_A : AddFreeGroup A X_A] β†’ [FAb_B : AddFreeGroup B X_B] β†’ (G : Type) β†’ [inst_2 : AddCommGroup G] β†’ (X_A βŠ• X_B β†’ G) β†’ A Γ— B β†’+ G
inducedProdHom
induced_extends :=
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f : X_A βŠ• X_B β†’ A_1), ↑(inducedProdHom A_1 f) ∘ ΞΉ = f
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝


↑(inducedProdHom A✝ f) ∘ ΞΉ = f
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f : X_A βŠ• X_B β†’ A_1), ↑(inducedProdHom A_1 f) ∘ ΞΉ = f
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

x: X_A βŠ• X_B


h
Function.comp (↑(inducedProdHom A✝ f)) ΞΉ x = f x
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

x: X_A βŠ• X_B


h
Function.comp (↑(inducedProdHom A✝ f)) ΞΉ x = f x
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f : X_A βŠ• X_B β†’ A_1), ↑(inducedProdHom A_1 f) ∘ ΞΉ = f
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

val✝: X_A


h.inl
Function.comp (↑(inducedProdHom A✝ f)) ΞΉ (Sum.inl val✝) = f (Sum.inl val✝)
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

val✝: X_B


h.inr
Function.comp (↑(inducedProdHom A✝ f)) ΞΉ (Sum.inr val✝) = f (Sum.inr val✝)
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

x: X_A βŠ• X_B


h
Function.comp (↑(inducedProdHom A✝ f)) ΞΉ x = f x
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

val✝: X_A


h.inl
Function.comp (↑(inducedProdHom A✝ f)) ΞΉ (Sum.inl val✝) = f (Sum.inl val✝)
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

val✝: X_B


h.inr
Function.comp (↑(inducedProdHom A✝ f)) ΞΉ (Sum.inr val✝) = f (Sum.inr val✝)
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

x: X_A βŠ• X_B


h
Function.comp (↑(inducedProdHom A✝ f)) ΞΉ x = f x
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

val✝: X_B


h.inr
↑(inducedHom A✝ (f ∘ Sum.inr)) (AddFreeGroup.ΞΉ val✝) = f (Sum.inr val✝)
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f : X_A βŠ• X_B β†’ A_1), ↑(inducedProdHom A_1 f) ∘ ΞΉ = f
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

val✝: X_A


h.inl
↑(inducedHom A✝ (f ∘ Sum.inl)) (AddFreeGroup.ΞΉ val✝) = f (Sum.inl val✝)
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

val✝: X_B


h.inr
↑(inducedHom A✝ (f ∘ Sum.inr)) (AddFreeGroup.ΞΉ val✝) = f (Sum.inr val✝)

Goals accomplished! πŸ™
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f : X_A βŠ• X_B β†’ A_1), ↑(inducedProdHom A_1 f) ∘ ΞΉ = f
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f: X_A βŠ• X_B β†’ A✝

val✝: X_B


h.inr
↑(inducedHom A✝ (f ∘ Sum.inr)) (AddFreeGroup.ΞΉ val✝) = f (Sum.inr val✝)

Goals accomplished! πŸ™
unique_extension :=
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f g : A Γ— B β†’+ A_1), ↑f ∘ ΞΉ = ↑g ∘ ΞΉ β†’ f = g
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ


f = g
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f g : A Γ— B β†’+ A_1), ↑f ∘ ΞΉ = ↑g ∘ ΞΉ β†’ f = g
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


h.mk
↑f (a, b) = ↑g (a, b)
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f g : A Γ— B β†’+ A_1), ↑f ∘ ΞΉ = ↑g ∘ ΞΉ β†’ f = g
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


h.mk
↑f (a, b) = ↑g (a, b)
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


h.mk
↑f (a, b) = ↑g (a, b)

Goals accomplished! πŸ™
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


h.mk
↑f ((a, 0) + (0, b)) = ↑g ((a, 0) + (0, b))
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


h.mk
↑f (a, b) = ↑g (a, b)
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


h.mk
↑f (a, 0) + ↑f (0, b) = ↑g ((a, 0) + (0, b))
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


h.mk
↑f (a, b) = ↑g (a, b)
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


h.mk
↑f (a, 0) + ↑f (0, b) = ↑g (a, 0) + ↑g (0, b)
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


h.mk
↑f (a, 0) + ↑f (0, b) = ↑g (a, 0) + ↑g (0, b)
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f g : A Γ— B β†’+ A_1), ↑f ∘ ΞΉ = ↑g ∘ ΞΉ β†’ f = g
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


h.mk
↑f (a, 0) + ↑f (0, b) = ↑g (a, 0) + ↑g (0, b)
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


a
↑(AddMonoidHom.comp f (AddMonoidHom.inl A B)) ∘ AddFreeGroup.ΞΉ = ↑(AddMonoidHom.comp g (AddMonoidHom.inl A B)) ∘ AddFreeGroup.ΞΉ
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


a
↑(AddMonoidHom.comp f (AddMonoidHom.inl A B)) ∘ AddFreeGroup.ΞΉ = ↑(AddMonoidHom.comp g (AddMonoidHom.inl A B)) ∘ AddFreeGroup.ΞΉ
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B


A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

x_A: X_A


a.h
Function.comp (↑(AddMonoidHom.comp f (AddMonoidHom.inl A B))) AddFreeGroup.ΞΉ x_A = Function.comp (↑(AddMonoidHom.comp g (AddMonoidHom.inl A B))) AddFreeGroup.ΞΉ x_A
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

x_A: X_A


a.h
Function.comp (↑(AddMonoidHom.comp f (AddMonoidHom.inl A B))) AddFreeGroup.ΞΉ x_A = Function.comp (↑(AddMonoidHom.comp g (AddMonoidHom.inl A B))) AddFreeGroup.ΞΉ x_A
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B



Goals accomplished! πŸ™
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f g : A Γ— B β†’+ A_1), ↑f ∘ ΞΉ = ↑g ∘ ΞΉ β†’ f = g
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)


h.mk
↑f (a, 0) + ↑f (0, b) = ↑g (a, 0) + ↑g (0, b)
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)


A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)


a
↑(AddMonoidHom.comp f (AddMonoidHom.inr A B)) ∘ AddFreeGroup.ΞΉ = ↑(AddMonoidHom.comp g (AddMonoidHom.inr A B)) ∘ AddFreeGroup.ΞΉ
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)


a
↑(AddMonoidHom.comp f (AddMonoidHom.inr A B)) ∘ AddFreeGroup.ΞΉ = ↑(AddMonoidHom.comp g (AddMonoidHom.inr A B)) ∘ AddFreeGroup.ΞΉ
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)


A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)

x_B: X_B


a.h
Function.comp (↑(AddMonoidHom.comp f (AddMonoidHom.inr A B))) AddFreeGroup.ΞΉ x_B = Function.comp (↑(AddMonoidHom.comp g (AddMonoidHom.inr A B))) AddFreeGroup.ΞΉ x_B
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)

x_B: X_B


a.h
Function.comp (↑(AddMonoidHom.comp f (AddMonoidHom.inr A B))) AddFreeGroup.ΞΉ x_B = Function.comp (↑(AddMonoidHom.comp g (AddMonoidHom.inr A B))) AddFreeGroup.ΞΉ x_B
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)



Goals accomplished! πŸ™
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f g : A Γ— B β†’+ A_1), ↑f ∘ ΞΉ = ↑g ∘ ΞΉ β†’ f = g
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)

B_unique: AddMonoidHom.comp f (AddMonoidHom.inr A B) = AddMonoidHom.comp g (AddMonoidHom.inr A B)


h.mk
A: Type ?u.14585

B: Type ?u.14588

inst✝¹: AddCommGroup A

inst✝: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B


βˆ€ {A_1 : Type} [inst : AddCommGroup A_1] (f g : A Γ— B β†’+ A_1), ↑f ∘ ΞΉ = ↑g ∘ ΞΉ β†’ f = g
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)

B_unique: AddMonoidHom.comp f (AddMonoidHom.inr A B) = AddMonoidHom.comp g (AddMonoidHom.inr A B)


h.mk
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)

B_unique: AddMonoidHom.comp f (AddMonoidHom.inr A B) = AddMonoidHom.comp g (AddMonoidHom.inr A B)


h.mk
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)

B_unique: AddMonoidHom.comp f (AddMonoidHom.inr A B) = AddMonoidHom.comp g (AddMonoidHom.inr A B)


h.mk
A: Type ?u.14585

B: Type ?u.14588

inst✝²: AddCommGroup A

inst✝¹: AddCommGroup B

X_A: Type ?u.14597

X_B: Type ?u.14600

FAb_A: AddFreeGroup A X_A

FAb_B: AddFreeGroup B X_B

A✝: Type

inst✝: AddCommGroup A✝

f, g: A Γ— B β†’+ A✝

hyp: ↑f ∘ ΞΉ = ↑g ∘ ΞΉ

a: A

b: B

A_unique: AddMonoidHom.comp f (AddMonoidHom.inl A B) = AddMonoidHom.comp g (AddMonoidHom.inl A B)

B_unique: AddMonoidHom.comp f (AddMonoidHom.inr A B) = AddMonoidHom.comp g (AddMonoidHom.inr A B)


h.mk

Goals accomplished! πŸ™
} end AddFreeGroup.Product