Zulip Chat Archive

Stream: new members

Topic: Trouble with a String Matching Function


Colin Jones ⚛️ (Sep 13 2024 at 13:29):

How do I get this to work?

def mwe := { s : String // s.length == 2 && s.dropWhile "AB".toList.contains == ""}

def AA : mwe := "AA", by rfl
def AB : mwe := "AB", by rfl
def BA : mwe := "BA", by rfl
def BB : mwe := "BB", by rfl

def matcher (s : mwe) :=
  match s with
  | AA => "1"
  | AB => "2"
#eval matcher AA
#eval matcher AB

I want the s variable to match with the AB I defined earlier not with the type itself.

Colin Jones ⚛️ (Sep 13 2024 at 13:30):

I want #eval matcher AB to output 2 not 1.

Daniel Weber (Sep 13 2024 at 14:05):

Is

def matcher (s : mwe) :=
  match s with
  | "AA", _⟩ => "1"
  | "AB", _⟩ => "2"
  | _ => ""
#eval matcher AA
#eval matcher AB

good, or are you looking for something else?

Tomas Skrivan (Sep 13 2024 at 15:29):

I think adding @[match_pattern] to definitions of AA and AB will make your original code work.

Colin Jones ⚛️ (Sep 17 2024 at 16:06):

Sorry for responding so late. Thank you both for replying. For the first one, is there a way I can prove that there are no other mwes other than "AB", "AA", "BB", "BA" so I don't have to include the miscellaneous case | _ => ""? Something like this:

def matcher (s : mwe) :=
  match s with
  | "AA", _⟩ => "1"
  | "AB", _⟩ => "2"
  | "BB", _⟩ => "3"
  | "BA", _⟩ => "4"

Also @[match_pattern] does work too:

@[match_pattern]
def AA : mwe := "AA", by rfl
@[match_pattern]
def AB : mwe := "AB", by rfl
@[match_pattern]
def BA : mwe := "BA", by rfl
@[match_pattern]
def BB : mwe := "BB", by rfl

def matcher' (s : mwe) :=
  match s with
  | AA => "1"
  | AB => "2"
  | _ => ""

Kevin Buzzard (Sep 17 2024 at 17:53):

You can prove there are no other mwes but then you'd still have to include what you call the miscellaneous case, you would just insert your proof there to show that it doesn't need to be dealt with.

Colin Jones ⚛️ (Sep 26 2024 at 01:36):

Would it be possible to prove that AA does not equal AB e.g.

def mwe := { s : String // s.length == 2 && s.dropWhile "AB".toList.contains == ""}

@[match_pattern]
def AA : mwe := "AA", by rfl
@[match_pattern]
def AB : mwe := "AB", by rfl

example : AA  AB := by
  simp only [ne_eq, AB, AA, String.toList, Char.isValue]
  sorry

Colin Jones ⚛️ (Sep 27 2024 at 03:40):

Would proving this even be possible? I can't separate the string part from the proof part

Daniel Weber (Sep 27 2024 at 03:43):

You can do this:

example : AA  AB := by
  intro h
  simpa [AA, AB] using congrArg Subtype.val h

Colin Jones ⚛️ (Sep 27 2024 at 03:45):

Thank you I would've spend decades trying to find this. Speaking of how did you find that solution so fast?

Daniel Weber (Sep 27 2024 at 03:51):

Using Mathlib tactics a simpler solution (which I also found first) is:

import Mathlib.Tactic.ApplyFun

example : AA  AB := by
  apply_fun Subtype.val
  simp [AA, AB]

which essentially says "these values aren't equal because their Subtype.val is different" and then simp is capable of showing that.
Now that apply_fun can be replaced by "assume AA = AB, then by docs#congrArg we have AA.val = AB.val"

Colin Jones ⚛️ (Sep 27 2024 at 03:52):

Thank you

Daniel Weber (Sep 27 2024 at 03:52):

This can also be written as

example : AA  AB := by
  apply mt (congrArg Subtype.val)
  simp [AA, AB]

to more directly replicate apply_fun

Notification Bot (Oct 20 2024 at 11:17):

10 messages were moved from this topic to #new members > Faster Way to prove all possible elements in a set by Eric Wieser.


Last updated: May 02 2025 at 03:31 UTC