|
| 1 | +--- |
| 2 | +title: 729.我的日程安排表 I |
| 3 | +date: 2025-01-02 16:33:43 |
| 4 | +tags: [题解, LeetCode, 中等, 设计, 线段树, 数组, 二分查找, 有序集合, 模拟] |
| 5 | +--- |
| 6 | + |
| 7 | +# 【LetMeFly】729.我的日程安排表 I:既然是I,那就暴力模拟 |
| 8 | + |
| 9 | +力扣题目链接:[https://leetcode.cn/problems/my-calendar-i/](https://leetcode.cn/problems/my-calendar-i/) |
| 10 | + |
| 11 | +<p>实现一个 <code>MyCalendar</code> 类来存放你的日程安排。如果要添加的日程安排不会造成 <strong>重复预订</strong> ,则可以存储这个新的日程安排。</p> |
| 12 | + |
| 13 | +<p>当两个日程安排有一些时间上的交叉时(例如两个日程安排都在同一时间内),就会产生 <strong>重复预订</strong> 。</p> |
| 14 | + |
| 15 | +<p>日程可以用一对整数 <code>startTime</code> 和 <code>endTime</code> 表示,这里的时间是半开区间,即 <code>[startTime, endTime)</code>, 实数 <code>x</code> 的范围为, <code>startTime <= x < endTime</code> 。</p> |
| 16 | + |
| 17 | +<p>实现 <code>MyCalendar</code> 类:</p> |
| 18 | + |
| 19 | +<ul> |
| 20 | + <li><code>MyCalendar()</code> 初始化日历对象。</li> |
| 21 | + <li><code>boolean book(int startTime, int endTime)</code> 如果可以将日程安排成功添加到日历中而不会导致重复预订,返回 <code>true</code> 。否则,返回 <code>false</code> 并且不要将该日程安排添加到日历中。</li> |
| 22 | +</ul> |
| 23 | + |
| 24 | +<p> </p> |
| 25 | + |
| 26 | +<p><strong class="example">示例:</strong></p> |
| 27 | + |
| 28 | +<pre> |
| 29 | +<strong>输入:</strong> |
| 30 | +["MyCalendar", "book", "book", "book"] |
| 31 | +[[], [10, 20], [15, 25], [20, 30]] |
| 32 | +<strong>输出:</strong> |
| 33 | +[null, true, false, true] |
| 34 | + |
| 35 | +<strong>解释:</strong> |
| 36 | +MyCalendar myCalendar = new MyCalendar(); |
| 37 | +myCalendar.book(10, 20); // return True |
| 38 | +myCalendar.book(15, 25); // return False ,这个日程安排不能添加到日历中,因为时间 15 已经被另一个日程安排预订了。 |
| 39 | +myCalendar.book(20, 30); // return True ,这个日程安排可以添加到日历中,因为第一个日程安排预订的每个时间都小于 20 ,且不包含时间 20 。</pre> |
| 40 | + |
| 41 | +<p> </p> |
| 42 | + |
| 43 | +<p><strong>提示:</strong></p> |
| 44 | + |
| 45 | +<ul> |
| 46 | + <li><code>0 <= start < end <= 10<sup>9</sup></code></li> |
| 47 | + <li>每个测试用例,调用 <code>book</code> 方法的次数最多不超过 <code>1000</code> 次。</li> |
| 48 | +</ul> |
| 49 | + |
| 50 | + |
| 51 | + |
| 52 | +## 解题方法:模拟 |
| 53 | + |
| 54 | +这道题是“日程安排**I**”,数据量是$10^3$量级的,$O(n^2)$时间复杂度的算法就能过。因此直接模拟就好了。 |
| 55 | + |
| 56 | +使用一个数组或两个数组记录每次成功被预定的起止时间,对于一个新的预定,如果与历史上每个起止时间都不冲突,则记入预定数组并返回`true`;否则返回`false`。 |
| 57 | + |
| 58 | +对于起止时间是`[s1, e1)`和`[s2, e2)`两个时间段,如何判断二者是否有冲突? |
| 59 | + |
| 60 | +> 如果`e1 > s2 且 e2 > s1`则有冲突。 |
| 61 | +> |
| 62 | +> 如果不理解,也可以使用下面是思路逆向推导: |
| 63 | +> |
| 64 | +> 两端时间没有交集说明`s1 >= e2 或 s2 >= e1`,对其取非就是了。 |
| 65 | +
|
| 66 | ++ 时间复杂度$O(n^2)$,其中$n$是调用总次数 |
| 67 | ++ 空间复杂度$O(n)$ |
| 68 | + |
| 69 | +### AC代码 |
| 70 | + |
| 71 | +#### C++ |
| 72 | + |
| 73 | +```cpp |
| 74 | +/* |
| 75 | + * @Author: LetMeFly |
| 76 | + * @Date: 2025-01-02 16:13:40 |
| 77 | + * @LastEditors: LetMeFly.xyz |
| 78 | + * @LastEditTime: 2025-01-02 16:15:23 |
| 79 | + */ |
| 80 | +class MyCalendar { |
| 81 | +private: |
| 82 | + vector<int> start, end; |
| 83 | +public: |
| 84 | + MyCalendar() { |
| 85 | + |
| 86 | + } |
| 87 | + |
| 88 | + bool book(int startTime, int endTime) { |
| 89 | + for (int i = 0; i < start.size(); i++) { |
| 90 | + if (!(end[i] <= startTime || endTime <= start[i])) { |
| 91 | + return false; |
| 92 | + } |
| 93 | + } |
| 94 | + start.push_back(startTime); |
| 95 | + end.push_back(endTime); |
| 96 | + return true; |
| 97 | + } |
| 98 | +}; |
| 99 | + |
| 100 | +/** |
| 101 | + * Your MyCalendar object will be instantiated and called as such: |
| 102 | + * MyCalendar* obj = new MyCalendar(); |
| 103 | + * bool param_1 = obj->book(startTime,endTime); |
| 104 | + */ |
| 105 | +``` |
| 106 | +
|
| 107 | +#### Python |
| 108 | +
|
| 109 | +```python |
| 110 | +''' |
| 111 | +Author: LetMeFly |
| 112 | +Date: 2025-01-02 16:16:58 |
| 113 | +LastEditors: LetMeFly.xyz |
| 114 | +LastEditTime: 2025-01-02 16:22:15 |
| 115 | +''' |
| 116 | +# 产生交集:!(e1 <= s2 || e2 <= s1) 等价于 e1 > s2 && e2 > s1 |
| 117 | +class MyCalendar: |
| 118 | +
|
| 119 | + def __init__(self): |
| 120 | + self.bookList = [] |
| 121 | +
|
| 122 | + def book(self, startTime: int, endTime: int) -> bool: |
| 123 | + if any(e > startTime and endTime > s for s, e in self.bookList): |
| 124 | + return False |
| 125 | + self.bookList.append((startTime, endTime)) |
| 126 | + return True |
| 127 | +
|
| 128 | +
|
| 129 | +# Your MyCalendar object will be instantiated and called as such: |
| 130 | +# obj = MyCalendar() |
| 131 | +# param_1 = obj.book(startTime,endTime) |
| 132 | +``` |
| 133 | + |
| 134 | +#### Java |
| 135 | + |
| 136 | +```java |
| 137 | +/* |
| 138 | + * @Author: LetMeFly |
| 139 | + * @Date: 2025-01-02 16:22:47 |
| 140 | + * @LastEditors: LetMeFly.xyz |
| 141 | + * @LastEditTime: 2025-01-02 16:27:07 |
| 142 | + */ |
| 143 | +import java.util.ArrayList; |
| 144 | + |
| 145 | +class MyCalendar { |
| 146 | + private ArrayList<Integer> start, end; |
| 147 | + |
| 148 | + public MyCalendar() { |
| 149 | + start = new ArrayList<Integer>(); |
| 150 | + end = new ArrayList<Integer>(); |
| 151 | + } |
| 152 | + |
| 153 | + public boolean book(int startTime, int endTime) { |
| 154 | + for (int i = 0; i < start.size(); i++) { |
| 155 | + if (end.get(i) > startTime && endTime > start.get(i)) { |
| 156 | + return false; |
| 157 | + } |
| 158 | + } |
| 159 | + start.add(startTime); |
| 160 | + end.add(endTime); |
| 161 | + return true; |
| 162 | + } |
| 163 | +} |
| 164 | + |
| 165 | +/** |
| 166 | + * Your MyCalendar object will be instantiated and called as such: |
| 167 | + * MyCalendar obj = new MyCalendar(); |
| 168 | + * boolean param_1 = obj.book(startTime,endTime); |
| 169 | + */ |
| 170 | +``` |
| 171 | + |
| 172 | +#### Go |
| 173 | + |
| 174 | +```go |
| 175 | +/* |
| 176 | + * @Author: LetMeFly |
| 177 | + * @Date: 2025-01-02 16:27:36 |
| 178 | + * @LastEditors: LetMeFly.xyz |
| 179 | + * @LastEditTime: 2025-01-02 16:32:36 |
| 180 | + */ |
| 181 | +package main |
| 182 | + |
| 183 | +type pair struct{ start, end int } |
| 184 | +type MyCalendar []pair |
| 185 | + |
| 186 | + |
| 187 | +func Constructor() MyCalendar { |
| 188 | + return MyCalendar{} |
| 189 | +} |
| 190 | + |
| 191 | + |
| 192 | +func (this *MyCalendar) Book(startTime int, endTime int) bool { |
| 193 | + for _, p := range *this { |
| 194 | + if endTime > p.start && p.end > startTime { |
| 195 | + return false |
| 196 | + } |
| 197 | + } |
| 198 | + *this = append(*this, pair{startTime, endTime}) |
| 199 | + return true |
| 200 | +} |
| 201 | + |
| 202 | + |
| 203 | +/** |
| 204 | + * Your MyCalendar object will be instantiated and called as such: |
| 205 | + * obj := Constructor(); |
| 206 | + * param_1 := obj.Book(startTime,endTime); |
| 207 | + */ |
| 208 | +``` |
| 209 | + |
| 210 | +> 同步发文于CSDN和我的[个人博客](https://blog.letmefly.xyz/),原创不易,转载经作者同意后请附上[原文链接](https://blog.letmefly.xyz/2025/01/02/LeetCode%200729.%E6%88%91%E7%9A%84%E6%97%A5%E7%A8%8B%E5%AE%89%E6%8E%92%E8%A1%A8I/)哦~ |
| 211 | +> |
| 212 | +> Tisfy:[https://letmefly.blog.csdn.net/article/details/144889921](https://letmefly.blog.csdn.net/article/details/144889921) |
0 commit comments