|
2 | 2 | import Std.Data.Iterators.Producers.Range |
3 | 3 | import Std |
4 | 4 |
|
5 | | -@[inline] |
6 | | -def intercalateIter {α : Type} [Std.Iterator α Id String.Slice] [Std.IteratorLoop α Id Id] |
7 | | - (s : String.Slice) (it : Std.Iter (α := α) String.Slice) : String := |
8 | | - (it.fold (init := none) (fun | none, sl => some sl.copy | some str, sl => str ++ s ++ sl)).getD "" |
9 | | - |
10 | 5 | def stringSequence (n : Nat) : String := |
11 | | - intercalateIter " " ((0...=n).iter.map (String.toSlice ∘ Nat.repr)) |
| 6 | + Std.Iter.intercalateString.{0} " " ((0...=n).iter.map (String.toSlice ∘ Nat.repr)) |
12 | 7 |
|
13 | 8 | example : stringSequence 0 = "0" := by native_decide |
14 | 9 | example : stringSequence 3 = "0 1 2 3" := by native_decide |
15 | 10 | example : stringSequence 10 = "0 1 2 3 4 5 6 7 8 9 10" := by native_decide |
16 | 11 |
|
17 | | -theorem String.intercalate_append_of_ne_nil {l m : List String} {s : String} (hl : l ≠ []) (hm : m ≠ []) : |
18 | | - s.intercalate (l ++ m) = s.intercalate l ++ s ++ s.intercalate m := by |
19 | | - induction l with |
20 | | - | nil => simp_all |
21 | | - | cons hd tl ih => |
22 | | - rw [List.cons_append, String.intercalate_cons_of_ne_nil (by simp_all)] |
23 | | - by_cases ht : tl = [] |
24 | | - · simp_all |
25 | | - · simp [ih ht, String.intercalate_cons_of_ne_nil ht, String.append_assoc] |
26 | | - |
27 | | -@[simp] |
28 | | -theorem intercalateIter_eq {α : Type} [Std.Iterator α Id String.Slice] [Std.Iterators.Finite α Id] |
29 | | - [Std.IteratorLoop α Id Id] [Std.LawfulIteratorLoop α Id Id] {s : String.Slice} {it : Std.Iter (α := α) String.Slice} : |
30 | | - intercalateIter s it = s.intercalate it.toList := by |
31 | | - simp only [intercalateIter, String.appendSlice_eq, ← Std.Iter.foldl_toList, |
32 | | - String.Slice.intercalate_eq] |
33 | | - generalize s.copy = s |
34 | | - have := congrArg (·.getD "") (List.foldl_map (init := none) (l := it.toList) (f := String.Slice.copy) |
35 | | - (g := (fun | none, t => some t | some str, t => str ++ s ++ t))) |
36 | | - refine Eq.trans ?_ (Eq.trans this.symm ?_) |
37 | | - · congr |
38 | | - grind |
39 | | - · suffices ∀ (l m : List String), |
40 | | - (l.foldl (init := if m = [] then none else some (s.intercalate m)) (fun | none, sl => some sl | some str, sl => str ++ s ++ sl)).getD "" |
41 | | - = s.intercalate (m ++ l) by |
42 | | - simpa using this (it.toList.map String.Slice.copy) [] |
43 | | - clear this |
44 | | - intro l m |
45 | | - induction l generalizing m with |
46 | | - | nil => cases m <;> simp |
47 | | - | cons hd tl ih => |
48 | | - rw [List.append_cons, ← ih, List.foldl_cons] |
49 | | - congr |
50 | | - simp only [List.append_eq_nil_iff, List.cons_ne_self, and_false, ↓reduceIte] |
51 | | - match m with |
52 | | - | [] => simp |
53 | | - | x::xs => |
54 | | - simp only [reduceCtorEq, ↓reduceIte, List.cons_append, Option.some.injEq] |
55 | | - rw [← List.cons_append, String.intercalate_append_of_ne_nil (by simp) (by simp), |
56 | | - String.intercalate_singleton] |
57 | | - |
58 | | -@[simp] |
59 | | -theorem String.Slice.toNat?_comp_copy : String.toNat? ∘ String.Slice.copy = String.Slice.toNat? := by |
60 | | - ext; simp |
61 | | - |
62 | 12 | /-- Calling `stringSequence` and then splitting the result at space characters and attempting to |
63 | 13 | parse the components into natural numbers yields the sequence `[some 0, some 1, ..., some n]`. -/ |
64 | 14 | theorem map_ofNat?_stringSequence {n : Nat} : |
65 | 15 | ((stringSequence n).split ' ').toList.map String.Slice.toNat? = |
66 | 16 | (0...=n).toList.map Option.some := by |
67 | | - rw [stringSequence, ← String.Slice.toNat?_comp_copy, ← List.map_map, intercalateIter_eq] |
68 | | - erw [String.Slice.toList_split_intercalate] |
| 17 | + rw [stringSequence, ← String.Slice.toNat?_comp_copy, ← List.map_map, |
| 18 | + Std.Iter.intercalateString_eq, String.Slice.toStringToString_eq, String.copy_toSlice] |
| 19 | + simp +instances only [String.reduceToSingleton] |
| 20 | + rw [String.toList_split_intercalate] |
69 | 21 | · rw [Std.Iter.toList_map] |
70 | 22 | simp |
71 | 23 | · rw [Std.Iter.toList_map] |
|
0 commit comments