-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathsearch.xml
460 lines (225 loc) · 445 KB
/
search.xml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
<?xml version="1.0" encoding="utf-8"?>
<search>
<entry>
<title>闲暇时间的随手写</title>
<link href="/posts/e8b000e3.html"/>
<url>/posts/e8b000e3.html</url>
<content type="html"><![CDATA[<h1 id="2024-10-16"><a href="#2024-10-16" class="headerlink" title="2024/10/16"></a>2024/10/16</h1><h6 id="我们就是我们反复做的事情。"><a href="#我们就是我们反复做的事情。" class="headerlink" title="我们就是我们反复做的事情。"></a>我们就是我们反复做的事情。</h6><p>今天就算是一个开始吧,明天哔哩哔哩账户应该就6级了。</p><p>从七月初开始工作,至今已三个多月,工作的时间过得属实很快,不知不觉中就从指尖流淌而过,从周一到周五,和小学时期盼着周五快点到来一般。<br>但终究是不一样的,但说不出是何。</p><p>这篇随写起源于今早或是昨晚的一个兴起之念。这段时间想法越来越多,想表达的念头也愈发的多,断断续续,零零散散,以前总觉得这些是无意义的,记录起来也是枉然,回看也只是徒生尴尬。其实仔细想想,记录下来也是很好的。一些故事在记忆里愈发的模糊,就写在这里。</p><p>这一篇就这样吧。</p>]]></content>
<categories>
<category> 随记 </category>
<category> 碎碎念 </category>
</categories>
<tags>
<tag> 随记 </tag>
</tags>
</entry>
<entry>
<title>关于在WebPack以及NodeJs版本问题的一些坑</title>
<link href="/posts/a65f14fb.html"/>
<url>/posts/a65f14fb.html</url>
<content type="html"><![CDATA[<!-- markdownlint-disable MD025 --><h1 id="前言"><a href="#前言" class="headerlink" title="前言"></a>前言</h1><p>这是在一次更新NodeJs版本后项目出现的问题,具体为什么在最开始可以运行,后续出现依赖问题以及不得而知,<br>可能是因为更新了NodeJs版本,出现了不兼容问题,但是理论上来说,NodeJs的版本更新不会出现这种问题,<br>所以这里记录一下,以防以后再次出现这种问题。</p><h2 id="依赖问题描述"><a href="#依赖问题描述" class="headerlink" title="依赖问题描述"></a>依赖问题描述</h2><p>以及记不得最开始使用的NodeJs版本是多少了大概是16.20.0,然后更新到了18.16.0,然后就出现了问题,<br>在安装依赖的时候,会出现依赖安装失败问题,具体原因是html-webpack-plugin这个依赖我在这里使用的是5.5.0,<br>然后在安装的时候会出现这个问题,具体的错误信息如下:</p><figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br></pre></td><td class="code"><pre><span class="line">npm ERR! code ERESOLVE</span><br><span class="line">npm ERR! ERESOLVE unable to resolve dependency tree</span><br><span class="line">npm ERR!</span><br><span class="line">npm ERR! While resolving: [email protected]</span><br><span class="line">npm ERR! Found: [email protected]</span><br><span class="line">npm ERR! node_modules/html-webpack-plugin</span><br><span class="line">npm ERR! dev html-webpack-plugin@<span class="string">"^5.5.1"</span> from the root project</span><br><span class="line">npm ERR!</span><br><span class="line">npm ERR! Could not resolve dependency:</span><br><span class="line">npm ERR! peer html-webpack-plugin@<span class="string">"^3.0.0 || ^4.0.0"</span> from [email protected]</span><br><span class="line">npm ERR! node_modules/script-ext-html-webpack-plugin</span><br><span class="line">npm ERR! dev script-ext-html-webpack-plugin@<span class="string">"2.1.5"</span> from the root project</span><br><span class="line">npm ERR!</span><br><span class="line">npm ERR! Fix the upstream dependency conflict, or retry</span><br><span class="line">npm ERR! this <span class="built_in">command</span> with --force or --legacy-peer-deps</span><br><span class="line">npm ERR! to accept an incorrect (and potentially broken) dependency resolution.</span><br></pre></td></tr></table></figure><p>这里的意思是说,html-webpack-plugin这个依赖的版本是5.5.3,需要使用的webpack版本是5,但是在script-ext-html-webpack-plugin这个依赖中,<br>需要的版本是3.0.0或者4.0.0,但是这里的版本是webpack5,所以如果要解决这个问题,需要将html-webpack-plugin这个依赖的版本降低到4及以下。</p><h2 id="运行问题描述"><a href="#运行问题描述" class="headerlink" title="运行问题描述"></a>运行问题描述</h2><p>由于之前更新了NodeJs版本,所以在运行的时候会出现一些问题,具体的错误信息如下:</p><figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br></pre></td><td class="code"><pre><span class="line">node:internal/crypto/hash:71</span><br><span class="line"> this[kHandle] = new _Hash(algorithm, xofLen);</span><br><span class="line"> ^</span><br><span class="line"></span><br><span class="line">Error: error:0308010C:digital envelope routines::unsupported</span><br><span class="line"> at new Hash (node:internal/crypto/hash:71:19)</span><br><span class="line"> at Object.createHash (node:crypto:133:10)</span><br><span class="line"> at module.exports (C:\Users\Peridot\Escritorio\proyectos\DoneWithIt\node_modules\webpack\lib\util\createHash.js:135:53)</span><br><span class="line"> at NormalModule._initBuildHash (C:\Users\Peridot\Escritorio\proyectos\DoneWithIt\node_modules\webpack\lib\NormalModule.js:417:16)</span><br><span class="line"> at handleParseError (C:\Users\Peridot\Escritorio\proyectos\DoneWithIt\node_modules\webpack\lib\NormalModule.js:471:10)</span><br><span class="line"> at C:\Users\Peridot\Escritorio\proyectos\DoneWithIt\node_modules\webpack\lib\NormalModule.js:503:5</span><br><span class="line"> at C:\Users\Peridot\Escritorio\proyectos\DoneWithIt\node_modules\webpack\lib\NormalModule.js:358:12</span><br><span class="line"> at C:\Users\Peridot\Escritorio\proyectos\DoneWithIt\node_modules\loader-runner\lib\LoaderRunner.js:373:3</span><br><span class="line"> at iterateNormalLoaders (C:\Users\Peridot\Escritorio\proyectos\DoneWithIt\node_modules\loader-runner\lib\LoaderRunner.js:214:10)</span><br><span class="line"> at Array.<anonymous> (C:\Users\Peridot\Escritorio\proyectos\DoneWithIt\node_modules\loader-runner\lib\LoaderRunner.js:205:4)</span><br><span class="line"> at Storage.finished (C:\Users\Peridot\Escritorio\proyectos\DoneWithIt\node_modules\enhanced-resolve\lib\CachedInputFileSystem.js:55:16)</span><br><span class="line"> at C:\Users\Peridot\Escritorio\proyectos\DoneWithIt\node_modules\enhanced-resolve\lib\CachedInputFileSystem.js:91:9</span><br><span class="line"> at C:\Users\Peridot\Escritorio\proyectos\DoneWithIt\node_modules\graceful-fs\graceful-fs.js:123:16</span><br><span class="line"> at FSReqCallback.readFileAfterClose [as oncomplete] (node:internal/fs/read_file_context:68:3) {</span><br><span class="line"> opensslErrorStack: [ <span class="string">'error:03000086:digital envelope routines::initialization error'</span> ],</span><br><span class="line"> library: <span class="string">'digital envelope routines'</span>,</span><br><span class="line"> reason: <span class="string">'unsupported'</span>,</span><br><span class="line"> code: <span class="string">'ERR_OSSL_EVP_UNSUPPORTED'</span></span><br><span class="line">}</span><br><span class="line"></span><br><span class="line">Node.js v18.12.1</span><br></pre></td></tr></table></figure><p>在这里的错误信息中,可以看到,这里的错误信息是在crypto这个模块中出现的,具体的错误信息是说,这个模块中的hash方法出现了问题,<br>这个方法是用来加密的,但是在这里出现了不支持的错误,这个错误的原因是从NodeJs版本 17 开始,NodeJs从 OpenSSL1.1.1 升级到 OpenSSL3。OpenSSL3不支持一些旧的哈希技术。这就是为什么我们面临这个错误“ERR_OSSL_EVP_UNSUPPORTED”。如果不想降低NodeJs版本,我们就需要在终端在设置NodeJs需要使用的OpenSSL版本,具体的命令如下:</p><figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="built_in">export</span> NODE_OPTIONS=--openssl-legacy-provider</span><br></pre></td></tr></table></figure><p>这样子,当我们再次运行的时候,就不会出现这个问题了。</p><h2 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h2><p>这个问题困扰了我很久很久,前端的项目依赖相对与Java来说要混乱很多,这也就是package-lock.json 的存在原因,避免随着依赖的变更导致项目无法运行。虽然新的版本会有更好的优化以及新功能,但是偶尔会废弃一些旧的功能,我们在新版本的环境是,可能就会出现不兼容问题了,所以在选择升级之前一定要搞清楚每一次的更新细节,更改了什么,废弃了什么,这样子才能避免一些不必要的问题。</p>]]></content>
<categories>
<category> 编程 </category>
<category> 前端 </category>
<category> Vue </category>
</categories>
<tags>
<tag> NodeJs </tag>
<tag> NPM </tag>
<tag> Vue </tag>
</tags>
</entry>
<entry>
<title>Linux 命令</title>
<link href="/posts/9da1ef6b.html"/>
<url>/posts/9da1ef6b.html</url>
<content type="html"><![CDATA[]]></content>
<categories>
<category> 随记 </category>
</categories>
<tags>
<tag> Linux </tag>
</tags>
</entry>
<entry>
<title>SpringBoot</title>
<link href="/posts/6f2612a2.html"/>
<url>/posts/6f2612a2.html</url>
<content type="html"><![CDATA[<p>关于文件上传</p><p>Html部分</p><figure class="highlight html"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta"><!DOCTYPE <span class="keyword">html</span>></span></span><br><span class="line"><span class="tag"><<span class="name">html</span> <span class="attr">lang</span>=<span class="string">"en"</span>></span></span><br><span class="line"><span class="tag"><<span class="name">head</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">meta</span> <span class="attr">charset</span>=<span class="string">"UTF-8"</span> <span class="attr">content</span>=<span class="string">"application/json"</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">title</span>></span>表单<span class="tag"></<span class="name">title</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">link</span> <span class="attr">rel</span>=<span class="string">"shortcut icon"</span> <span class="attr">th:href</span>=<span class="string">"@{/static/favicon.png}"</span>/></span></span><br><span class="line"><span class="tag"></<span class="name">head</span>></span></span><br><span class="line"><span class="tag"><<span class="name">script</span> <span class="attr">src</span>=<span class="string">"https://cdnjs.cloudflare.com/ajax/libs/jquery/3.6.1/jquery.min.js"</span>></span></span><br><span class="line"><span class="tag"></<span class="name">script</span>></span></span><br><span class="line"><span class="tag"><<span class="name">body</span>></span></span><br><span class="line"><span class="tag"><<span class="name">div</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">form</span> <span class="attr">id</span>=<span class="string">"uploadImage"</span> <span class="attr">action</span>=<span class="string">"http://localhost:8080/upData"</span> <span class="attr">method</span>=<span class="string">"post"</span> <span class="attr">enctype</span>=<span class="string">"multipart/form-data"</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">label</span>></span></span><br><span class="line"> Images</span><br><span class="line"> <span class="tag"><<span class="name">input</span> <span class="attr">id</span>=<span class="string">"image"</span> <span class="attr">name</span>=<span class="string">"file"</span> <span class="attr">type</span>=<span class="string">"file"</span> <span class="attr">accept</span>=<span class="string">"image/gif, image/jpg, image/png"</span>/></span></span><br><span class="line"> <span class="tag"></<span class="name">label</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">input</span> <span class="attr">type</span>=<span class="string">"submit"</span> <span class="attr">value</span>=<span class="string">"提交图片"</span>/></span></span><br><span class="line"> <span class="tag"></<span class="name">form</span>></span></span><br><span class="line"><span class="tag"></<span class="name">div</span>></span></span><br><span class="line"><span class="comment"><!-- 用于实时显示用户上传图片,提供及时反馈 --></span></span><br><span class="line"><span class="tag"><<span class="name">img</span> <span class="attr">id</span>=<span class="string">"images"</span> <span class="attr">src</span>=<span class="string">""</span> <span class="attr">alt</span>=<span class="string">""</span> <span class="attr">style</span>=<span class="string">"width: 100px;height: 100px;visibility: collapse"</span>></span></span><br><span class="line"><span class="tag"></<span class="name">body</span>></span></span><br><span class="line"><span class="tag"></<span class="name">html</span>></span></span><br></pre></td></tr></table></figure><p>这里的enctype很重要<br>官方解释:</p><figure class="highlight text"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">enctype:</span><br><span class="line">如果method属性的值为post ,则enctype是表单提交的MIME 类型 。可能的值:</span><br><span class="line">application/x-www-form-urlencoded :默认值。</span><br><span class="line">multipart/form-data :如果表单包含type=file的<input>元素,则使用此选项。</span><br><span class="line">text/plain :由 HTML5 引入,用于调试目的。</span><br><span class="line">该值可以被<button> 、 <input type="submit"> 或<input type="image"> 元素上的formenctype属性覆盖。</span><br></pre></td></tr></table></figure><p>当我们提交的是带有文件的提交时,我们就需要使用multipart/form-data</p><p>后端继承自SpringBoot<br>代码如下:<br>这里上传的文件会存储在项目同级目录下的static下</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@CrossOrigin</span></span><br><span class="line"><span class="meta">@PostMapping("/upData")</span></span><br><span class="line"><span class="keyword">public</span> String <span class="title function_">upload</span><span class="params">(<span class="meta">@RequestParam("file")</span> MultipartFile file)</span> <span class="keyword">throws</span> IOException {</span><br><span class="line"> <span class="type">String</span> <span class="variable">originalFilename</span> <span class="operator">=</span> file.getOriginalFilename();</span><br><span class="line"> <span class="type">String</span> <span class="variable">FileType</span> <span class="operator">=</span> originalFilename.substring(originalFilename.lastIndexOf(<span class="string">"."</span>));</span><br><span class="line"> <span class="type">String</span> <span class="variable">NewFileName</span> <span class="operator">=</span> UUID.randomUUID() + FileType;</span><br><span class="line"> <span class="type">String</span> <span class="variable">dir</span> <span class="operator">=</span> ResourceUtils.getURL(<span class="string">"classpath:"</span>).getPath();</span><br><span class="line"> String[] targets = dir.split(<span class="string">"target"</span>);</span><br><span class="line"> String[] split = targets[<span class="number">0</span>].split(<span class="string">"file:/"</span>);</span><br><span class="line"> <span class="type">String</span> <span class="variable">newDir</span> <span class="operator">=</span> split[<span class="number">1</span>];</span><br><span class="line"> <span class="type">String</span> <span class="variable">decode</span> <span class="operator">=</span> URLDecoder.decode(newDir, <span class="string">"utf-8"</span>);</span><br><span class="line"> <span class="type">File</span> <span class="variable">Path</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">File</span>(decode + <span class="string">"/static/"</span> + NewFileName);</span><br><span class="line"> System.out.println(Path.getPath());</span><br><span class="line"> <span class="keyword">if</span> (!Path.exists()) {</span><br><span class="line"> Path.mkdirs();</span><br><span class="line"> }</span><br><span class="line"> file.transferTo(Path);</span><br><span class="line"> System.out.println(<span class="string">"上传成功"</span>);</span><br><span class="line"> <span class="keyword">return</span> <span class="string">"Success"</span>+Path.getPath();</span><br><span class="line">}</span><br></pre></td></tr></table></figure>]]></content>
<categories>
<category> SpringBoot UpLoad </category>
</categories>
<tags>
<tag> SpringBoot Html </tag>
</tags>
</entry>
<entry>
<title>Git小知识</title>
<link href="/posts/9b0be8b0.html"/>
<url>/posts/9b0be8b0.html</url>
<content type="html"><![CDATA[<p>初始化git仓库</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git init</span><br></pre></td></tr></table></figure><p>已经有远程仓库,想要clone到本地<br>lone 的仓库不需要进行上下游链接</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git clone <Repository_link></span><br></pre></td></tr></table></figure><p>不clone 链接远程仓库</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git remote add <Repository_link></span><br></pre></td></tr></table></figure><p>创建分支</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git branch <branch name></span><br></pre></td></tr></table></figure><p>切换分支</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git checkout <branch name></span><br></pre></td></tr></table></figure><p>删除本地分支 : 如分支名为dev</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">git branch -D dev</span><br><span class="line">它会直接删除,不检查</span><br></pre></td></tr></table></figure><p>创建远程分支</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git push origin <branch Name></span><br></pre></td></tr></table></figure><p>创建远程分支后要记得进行上下游链接</p><p>设置上游远程分支<br>方式一(适用远程分支已存在):<br>用参数 -u 或 —set-upstream-to 设置上游</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git branch --set-upstream-to=origin/<远程分支> <本地分支></span><br></pre></td></tr></table></figure><p>方式二(适用远程分支不存在):</p><p>上传本地分支到远程,同是把上传后的远程分支设置为本地分支的上游分支:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git push set-upstream origin HEAD:<远程分支></span><br></pre></td></tr></table></figure><p> 取消分支上游:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git branch --unset-upstream</span><br></pre></td></tr></table></figure><p>删除远程分支</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git push origin -d dev</span><br></pre></td></tr></table></figure><p>查看上游:<br>可以通过git status 、 git checkout <分支>、git branch -vv命令查看</p><p>清理本地不存在的远程分支,如别人删除了dev,但是你本地查看还有,就可以执行该条命令</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git remote prune origin</span><br></pre></td></tr></table></figure><p>合并分支</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git merge [merge-Branch-Name]</span><br></pre></td></tr></table></figure><p>合并之后,我们应该就不再需要这个分支了,可以删除</p><p>合并冲突<br>如果git此时无法自动进行合并操作,我们可以在任意时刻使用git status命令查看那些因为包含合并冲突而处于未合并状态的文件</p><p>任何因包含合并冲突而有待解决的文件,都会以未合并状态标识出来。 Git 会在有冲突的文件中加入标准的冲突解决标记,这样你可以打开这些包含冲突的文件然后手动解决冲突。 出现冲突的文件会包含一些特殊区段,看起来像下面这个样子:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><<<<<<< HEAD:index.html</span><br><span class="line"><div id="footer">contact : [email protected]</div></span><br><span class="line">=======</span><br><span class="line"><div id="footer"></span><br><span class="line"> please contact us at [email protected]</span><br><span class="line"></div></span><br><span class="line">>>>>>>> iss53:index.html</span><br></pre></td></tr></table></figure><p>这表示 HEAD 所指示的版本(也就是你的 master 分支所在的位置,因为你在运行 merge 命令的时候已经检出到了这个分支)在这个区段的上半部分(======= 的上半部分),而 iss53 分支所指示的版本在 ======= 的下半部分。 为了解决冲突,你必须选择使用由 ======= 分割的两部分中的一个,或者你也可以自行合并这些内容。 例如,你可以通过把这段内容换成下面的样子来解决冲突:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><div id="footer"></span><br><span class="line">please contact us at [email protected]</span><br><span class="line"></div></span><br></pre></td></tr></table></figure><p>上述的冲突解决方案仅保留了其中一个分支的修改,并且 <<<<<<< , ======= , 和 >>>>>>> 这些行被完全删除了。 在你解决了所有文件里的冲突之后,对每个文件使用 git add 命令来将其标记为冲突已解决。 一旦暂存这些原本有冲突的文件,Git 就会将它们标记为冲突已解决。</p><p>如果你对结果感到满意,并且确定之前有冲突的的文件都已经暂存了,这时你可以输入 git commit 来完成合并提交。 默认情况下提交信息看起来像下面这个样子:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br></pre></td><td class="code"><pre><span class="line">Merge branch 'iss53'</span><br><span class="line"></span><br><span class="line">Conflicts:</span><br><span class="line"> index.html</span><br><span class="line">#</span><br><span class="line"># It looks like you may be committing a merge.</span><br><span class="line"># If this is not correct, please remove the file</span><br><span class="line"># .git/MERGE_HEAD</span><br><span class="line"># and try again.</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"># Please enter the commit message for your changes. Lines starting</span><br><span class="line"># with '#' will be ignored, and an empty message aborts the commit.</span><br><span class="line"># On branch master</span><br><span class="line"># All conflicts fixed but you are still merging.</span><br><span class="line">#</span><br><span class="line"># Changes to be committed:</span><br><span class="line"># modified: index.html</span><br><span class="line">#</span><br></pre></td></tr></table></figure><p>变基</p><p>提取在 C4 中引入的补丁和修改,然后在 C3 的基础上应用一次。 在 Git 中,这种操作就叫做 变基(rebase)你可以使用 rebase 命令将提交到某一分支上的所有修改都移至另一分支上,就好像“重新播放”一样。</p><p>关于撤销操作<br>如果我们在提交之后突然发现少提交的了一些东西,或者想修改提交信息,我们可以使用 带< —amend > 参数的commit重复提交</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">git commit -m "You Commit Message"</span><br><span class="line">git add xxxxx</span><br><span class="line">git commit --amend</span><br></pre></td></tr></table></figure><p>最终你只会有一个提交——第二次提交将代替第一次提交的结果。</p><p>取消暂存区文件</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git reset <file name 如果指定文件 则指定取消暂存文件,否则取消当前分支的全部文件暂存></span><br></pre></td></tr></table></figure><p>撤销对文件的修改<br>其实< git status 告诉了我们可能使用什么命令></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git checkout -- files/file name</span><br></pre></td></tr></table></figure><p>标签<br>有时候我们需要给某个版本打上特定的标记/标签,我们可以使用</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git tag tag-name</span><br></pre></td></tr></table></figure><p>推送标签</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git push --tags</span><br></pre></td></tr></table></figure>]]></content>
<categories>
<category> Git </category>
</categories>
<tags>
<tag> Git </tag>
</tags>
</entry>
<entry>
<title>Git</title>
<link href="/posts/69c3279c.html"/>
<url>/posts/69c3279c.html</url>
<content type="html"><![CDATA[<!-- markdownlint-disable MD025 --><h1 id="序"><a href="#序" class="headerlink" title="序"></a>序</h1>]]></content>
<categories>
<category> Git </category>
</categories>
<tags>
<tag> Git </tag>
</tags>
</entry>
<entry>
<title>Android布局</title>
<link href="/posts/a9a74215.html"/>
<url>/posts/a9a74215.html</url>
<content type="html"><![CDATA[<!-- markdownlint-disable MD025 --><h1 id="Android-布局"><a href="#Android-布局" class="headerlink" title="Android 布局"></a>Android 布局</h1><h2 id="五种基础布局"><a href="#五种基础布局" class="headerlink" title="五种基础布局"></a>五种基础布局</h2><h3 id="1、LinearLayout-(线性布局)"><a href="#1、LinearLayout-(线性布局)" class="headerlink" title="1、LinearLayout (线性布局)"></a>1、LinearLayout (线性布局)</h3><blockquote><p>LinearLayout是一种线型的布局方式。LinearLayout布局容器内的组件一个挨着一个地排列起来:不仅可以控制个组件横向排列,也可控制各组件纵向排列。</p></blockquote><ul><li>android:orientation 属性指定了排列方向,可以选择vertical与horizontal</li><li>android:gravity 属性制定了文字在控件中的对齐方式,与HTML对齐方式大致相同</li><li>android:layout_gravity 属性和上面的属性看起来很像,但是多了一个layout前缀,因此他可以指定控件在布局中的对齐方式</li><li>android:layout_weight=”1”(权重),weight处于垂直布局时代表行距,水平布局时代表列宽,weight值越大则对应的行距或列宽越大</li><li>android:visibility=invisible控制布局是否显示 1、visible 显示 2、invisible 不显示但依旧占用布局空间 3、gone 隐藏控件</li></ul><h3 id="2、RelativeLayout(相对布局)"><a href="#2、RelativeLayout(相对布局)" class="headerlink" title="2、RelativeLayout(相对布局)"></a>2、RelativeLayout(相对布局)</h3><p>后续更新</p><h3 id="3、FrameLayout(帧布局)"><a href="#3、FrameLayout(帧布局)" class="headerlink" title="3、FrameLayout(帧布局)"></a>3、FrameLayout(帧布局)</h3><p>后续更新</p><h3 id="4、TableLayout(表格布局)GridLayout-网格布局"><a href="#4、TableLayout(表格布局)GridLayout-网格布局" class="headerlink" title="4、TableLayout(表格布局)GridLayout 网格布局"></a>4、TableLayout(表格布局)GridLayout 网格布局</h3><p>后续更新</p><h3 id="5、AbsoluteLayout(绝对布局)"><a href="#5、AbsoluteLayout(绝对布局)" class="headerlink" title="5、AbsoluteLayout(绝对布局)"></a>5、AbsoluteLayout(绝对布局)</h3><p>后续更新</p>]]></content>
<categories>
<category> 编程 </category>
<category> Android </category>
</categories>
<tags>
<tag> Android </tag>
<tag> 布局 </tag>
</tags>
</entry>
<entry>
<title>Android核心组件</title>
<link href="/posts/9490d20a.html"/>
<url>/posts/9490d20a.html</url>
<content type="html"><![CDATA[<!-- markdownlint-disable MD025 --><h1 id="Android四大组件分别为Activity、Service、Content-Provider、Broadcast-Receiver"><a href="#Android四大组件分别为Activity、Service、Content-Provider、Broadcast-Receiver" class="headerlink" title="Android四大组件分别为Activity、Service、Content Provider、Broadcast Receiver"></a>Android四大组件分别为Activity、Service、Content Provider、Broadcast Receiver</h1><h2 id="一、Activity组件"><a href="#一、Activity组件" class="headerlink" title="一、Activity组件"></a>一、Activity组件</h2><p>Activity的主要的作用就是一个Activity通常就是一个活动窗口,交互的载体。</p><p>一个Activity通常就是一个单独的屏幕(窗口)。<br>Activity之间通过Intent进行通信。<br>每一个Activity都必须要在AndroidManifest.xml配置文件中声明,否则系统将不识别也不执行该Activity。</p><h2 id="二、Service-服务"><a href="#二、Service-服务" class="headerlink" title="二、Service 服务"></a>二、Service 服务</h2><p>与Activity具备一个前台显示界面的活动组件不同,Android中有一个组件,没有显示画面,一般不需要与用户进行交互,该组件通常运行在后台,称之为Service服务组件。</p><p>如果想要实现自己自定义的Service,需要继承自系统的Service基类,同样也需要在清单文件AndroidMainfest.xml文件中进行声明。关于Service,可以简单总结如下:</p><p>Service通常用于在后台完成用户指定的操作。<br>Service也同样有生命周期,可以进行声明周期的管理。<br>Service分为两类:startService和bindService。<br>自定义实现的Service需要在清单配置文件中进行声明和注册。<br>startService<br>在其他组件(比如Activity)中通过startService启动一个后台服务组件,服务启动后,服务的生命周期和活动状态和启动该服务的组件不再有关系,即该服务的运行状态变得独立。</p><p>bindService<br>与startService方式启动的服务不同,如果是通过bindService启动某个服务组件,则意味着启动服务的组件和服务进行了绑定,存在一种绑定关系。如果某个时刻,调用者(比如说Activity)触法退出逻辑,关闭活动页面,则通过bindService绑定的服务也会随机停止。类似于“不求同年同月同日生生,但求同年同月同日生死”的悲壮。</p><h2 id="三、ContentProvider内容提供者"><a href="#三、ContentProvider内容提供者" class="headerlink" title="三、ContentProvider内容提供者"></a>三、ContentProvider内容提供者</h2><p>ContentProvider 通常被直译为内容提供者,组件名字很形象的诠释了该组件的作用。在Android系统中,每个应用程序是运行在不同的进程中,进程间是相互独立的。如果开发者开发的某一个应用程序,需要提供一些数据给其他应用程序,则可以通过ContentProvider将提供的数据进行暴露,其他应用程序通过ContentResolver从内容提供者中获取相应的数据。对Content Provider相关的内容进行总结:</p><p>A应用程序使用Content Provider提供共享数据,B应用程序通过Content Resolver按照规则获取数据。<br>只有需要在多个应用程序间共享数据时才需要内容提供者。例如,通讯录数据被多个应用程序使用,且必须存储在一个内容提供者中。它的好处是统一数据访问方式。<br>ContentProvider实现数据共享。<br>ContentProvider使用URI来唯一标识其数据集,这里的URI以content://作为前缀,表示该数据由ContentProvider来管理。<br>需要在清单配置文件中进行注册和声明。<br>四、Boradcast Receiver广播接受者<br>Android中的广播的工作方式类似于隐式Intent的工作方式,开发者可以指定接收一些事件,该事件既可以是自定义的,也可以是系统定义的。在程序运行时,可以根据指定的事件进行过滤和拦截,符合要求的事件,会被广播接收器接收,并执行相应的业务逻辑。Android系统中广播接收者的出现,实现了极大的模块的解耦。</p><p>对于广播接收者,总结如下:</p><p>广播接收者可以通过事件过滤和拦截,实现组件的通信。<br>广播接收者的注册有两种方式:动态注册(代码中注册)和静态注册(清单文件注册)。<br>动态注册:Activity关闭后,失效。静态注册:不会失效。</p>]]></content>
<categories>
<category> 编程 </category>
<category> Android </category>
</categories>
<tags>
<tag> Android </tag>
<tag> 组件 </tag>
</tags>
</entry>
<entry>
<title>Java JNA的使用</title>
<link href="/posts/45e49ef2.html"/>
<url>/posts/45e49ef2.html</url>
<content type="html"><![CDATA[<!-- markdownlint-disable MD025 --><h1 id="Java-JNA"><a href="#Java-JNA" class="headerlink" title="Java JNA"></a>Java JNA</h1><h2 id="简介"><a href="#简介" class="headerlink" title="简介"></a>简介</h2><p>JNA 全称‘Java Native Access’ 是一个建立在传统JNI技术上的Java开源框架。JNA提供了一组Java工具类用于运行期动态访问系统本地库(Native Library)而不需要编写任何Native、JNI代码。开发者只需要在Java接口中描述目标Native Library的函数与结构,JNA会自动实现Java接口到Native Function的映射。</p><p>1,dll和so是C函数的集合和容器,这与Java中的接口概念吻合,所以JNA把dll文件和so文件看成一个个接口。在JNA中定义一个接口就是相当于了定义一个DLL/SO文件的描述文件,该接口代表了动态链接库中发布的所有函数。而且,对于程序不需要的函数,可以不在接口中声明。</p><p>2,JNA定义的接口一般继承com.sun.jna.Library接口,如果dll文件中的函数是以stdcall方式输出函数,那么,该接口就应该继承com.sun.jna.win32.StdCallLibrary接口。</p><p>3,Jna难点:编程语言之间的数据类型不一致。</p><h2 id="类型对照"><a href="#类型对照" class="headerlink" title="类型对照"></a>类型对照</h2><div class="table-container"><table><thead><tr><th>Java类型</th><th>C类型</th><th>C类型原生表现</th></tr></thead><tbody><tr><td>boolean</td><td>int</td><td>32位整数(可定制)</td></tr><tr><td>byte</td><td>char</td><td>8位整数</td></tr><tr><td>char</td><td>wchar_t</td><td>平台依赖</td></tr><tr><td>short</td><td>short</td><td>16位整数</td></tr><tr><td>int</td><td>int</td><td>32位整数</td></tr><tr><td>long</td><td>long,__int64</td><td>64位整数</td></tr><tr><td>float</td><td>float</td><td>32位浮点数</td></tr><tr><td>double</td><td>double</td><td>64位浮点数</td></tr><tr><td>Buffer/Pointer</td><td>pointer</td><td>平台依赖(32或64位指针)</td></tr><tr><td></td><td>pointer/array</td><td>32或64位指针(参数/返回值)邻接内存(结构体成员)</td></tr><tr><td>String</td><td>char*</td><td>/0结束的数组(nativeencodingorjna.encoding)</td></tr><tr><td>WString</td><td>wchar_t*</td><td>/0结束的数组(unicode)</td></tr><tr><td>String[]</td><td>char**</td><td>/0结束的数组的数组</td></tr><tr><td>WString[]</td><td>wchar_t**</td><td>/0结束的宽字符数组的数组</td></tr><tr><td>Structure</td><td>struct*/struct</td><td>指向结构体的指针(参数或返回值)(或者明确指定是结构体指针)结构体(结构体的成员)(或者明确指定是结构体)</td></tr><tr><td>Union</td><td>union</td><td>等同于结构体</td></tr><tr><td>Structure[]</td><td>struct[]</td><td>结构体的数组,邻接内存</td></tr><tr><td>Callback</td><td>(*fp)()</td><td>Java函数指针或原生函数指针</td></tr><tr><td>NativeMapped</td><td>varies</td><td>依赖于定义</td></tr><tr><td>NativeLong</td><td>long</td><td>平台依赖(32或64位整数)</td></tr><tr><td>PointerType</td><td>pointer</td><td>和Pointer相同</td></tr></tbody></table></div><h2 id="案例"><a href="#案例" class="headerlink" title="案例"></a>案例</h2><p>下面的示例映射了标准C库中的printf函数并调用。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.sun.jna.examples;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> com.sun.jna.Library;</span><br><span class="line"><span class="keyword">import</span> com.sun.jna.Native;</span><br><span class="line"><span class="keyword">import</span> com.sun.jna.Platform;</span><br><span class="line"></span><br><span class="line"><span class="comment">/** JNA简单接口示例 */</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">HelloWorld</span> {</span><br><span class="line"></span><br><span class="line"> <span class="comment">// 这是标准的,稳定的映射方式,支持广泛</span></span><br><span class="line"> <span class="comment">// Java类型到Native类型的定制和映射</span></span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">interface</span> <span class="title class_">CLibrary</span> <span class="keyword">extends</span> <span class="title class_">Library</span> {</span><br><span class="line"> <span class="type">CLibrary</span> <span class="variable">INSTANCE</span> <span class="operator">=</span> (CLibrary)Native.load((Platform.isWindows() ? <span class="string">"msvcrt"</span> : <span class="string">"c"</span>),CLibrary.class);</span><br><span class="line"> <span class="keyword">void</span> <span class="title function_">printf</span><span class="params">(String format, Object... args)</span>;</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> {</span><br><span class="line"> CLibrary.INSTANCE.printf(<span class="string">"Hello, World\n"</span>);</span><br><span class="line"> <span class="keyword">for</span> (<span class="type">int</span> i=<span class="number">0</span>;i < args.length;i++) {</span><br><span class="line"> CLibrary.INSTANCE.printf(<span class="string">"Argument %d: %s\n"</span>, i, args[i]);</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><p>运行程序,如果不带参数就会单独打印“Hello,World”,如果带参则会打印出所有参数。由此可以看出,不需要写一行C代码,就可以直接在Java中调用外部动态链接库里的函数。<br>注意:参照上面的类型对照表,可以发现,传参不支持Class。</p><h3 id="关于C输出语句占位符"><a href="#关于C输出语句占位符" class="headerlink" title="关于C输出语句占位符"></a>关于C输出语句占位符</h3><div class="table-container"><table><thead><tr><th>格式</th><th>含义</th></tr></thead><tbody><tr><td>%d, %i</td><td>代表整数</td></tr><tr><td>%f</td><td>浮点</td></tr><tr><td>%s</td><td>字符串</td></tr><tr><td>%c</td><td>char</td></tr><tr><td>%p</td><td>指针</td></tr><tr><td>%fL</td><td>长log</td></tr><tr><td>%e</td><td>科学计数</td></tr><tr><td>%g</td><td>小数或科学计数。</td></tr><tr><td>%a,%A</td><td>读入一个浮点值(仅C99有效)。</td></tr><tr><td>%c</td><td>读入一个字符。</td></tr><tr><td>%d</td><td>读入十进制整数。</td></tr><tr><td>%i</td><td>读入十进制,八进制,十六进制整数。</td></tr><tr><td>%o</td><td>读入八进制整数。</td></tr><tr><td>%x,</td><td>%X 读入十六进制整数。</td></tr><tr><td>%s</td><td>读入一个字符串,遇空格、制表符或换行符结束。</td></tr><tr><td>%f,%F,%e,%E,%g,%G</td><td>用来输入实数,可以用小数形式或指数形式输入。</td></tr><tr><td>%p</td><td>读入一个指针。</td></tr><tr><td>%u</td><td>读入一个无符号十进制整数。</td></tr><tr><td>%n</td><td>至此已读入值的等价字符数。</td></tr><tr><td>%[]</td><td>扫描字符集合。</td></tr><tr><td>%%</td><td>读 % 符号</td></tr></tbody></table></div><h3 id="程序解读"><a href="#程序解读" class="headerlink" title="程序解读"></a>程序解读</h3><p>1、首先定义一个接口用于Native Function映射,继承自Library或StdCallLibrary<br>默认继承Library,如果dll中的函数是以stdcall方式调用,那么就继承StdCallLibrary,WIN32 Api都采用stdcall调用方式 就例如Windows中最为重要的kernel32库</p><p>2、接口内部定义<br>接口内部需要一个公共的静态常量:INSTANCE,通过这个常量我们可以获得这个接口的实例,从而使用接口的方法,也就是最关键的,调用外部dll/so的函数。该常量通过Native.load()静态函数获得,该函数的弃用方法为 <strong>Native.loadLibrary()</strong> 该函数有两个参数:</p><ul><li><p>第一个参数是动态链接库dll/so的名称,但不带.dll或.so这样的后缀,这符合JNI的规范,因为带了后缀名就不可以跨操作系统平台了。搜索动态链接库路径的顺序是:先从当前类的当前文件夹找,如果没有找到,再在工程当前文件夹下面找win32/win64文件夹,找到后搜索对应的dll文件,如果找不到再到WINDOWS下面去搜索,再找不到就会抛异常了。比如上例中printf函数在Windows平台下所在的dll库名称是msvcrt,而在其它平台如Linux下的so库名称是c。</p></li><li><p>第二个参数是本接口的Class类型。JNA通过这个Class类型,根据指定的.dll/.so文件,动态创建接口的实例。该实例由JNA通过反射自动生成。</p></li></ul><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="type">CLibrary</span> <span class="variable">getInstance</span> <span class="operator">=</span> (CLibrary) Native.load(Platform.isWindows() ? <span class="string">"msvcrt"</span> : <span class="string">"c"</span>, CLibrary.class);</span><br></pre></td></tr></table></figure><p>接口中只需要定义你要用到的函数或公共变量,不需要的可以不定义,如上面的例子之定义了printf函数</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">void</span> <span class="title function_">printf</span><span class="params">(String from, Object... args)</span>;</span><br></pre></td></tr></table></figure><p>定义的时候要注意参数和返回值的类型,需要同链接库中的函数类型保持一致</p><p>3、调用dll函数<br>定义好接口之后,我们就可以使用接口方法调用dll/so中相对应的函数了。</p><p>如果想调用自己实现的库函数,可以将自己实现的库函数编译成dll/so,放到当前目录下,然后和上述例子一样的去编写调用即可。</p><p>关于Windows下dll的函数导出列表可以自行查询。这里有一个网站记载了了Windows的所有<a href="http://windows10dll.nirsoft.net">dll</a></p><h2 id="JNA构造结构体"><a href="#JNA构造结构体" class="headerlink" title="JNA构造结构体"></a>JNA构造结构体</h2><p>在C里面没有Class类型,但是我们需要传递对象时可以通过转化为Struct</p>]]></content>
<categories>
<category> 编程 </category>
<category> Java </category>
</categories>
<tags>
<tag> JNA </tag>
<tag> Java </tag>
</tags>
</entry>
<entry>
<title>软件测试</title>
<link href="/posts/7a8ab919.html"/>
<url>/posts/7a8ab919.html</url>
<content type="html"><![CDATA[<!-- markdownlint-disable MD025 --><h1 id="软件测试"><a href="#软件测试" class="headerlink" title="软件测试"></a>软件测试</h1><h2 id="简介"><a href="#简介" class="headerlink" title="简介"></a>简介</h2><h3 id="生命周期"><a href="#生命周期" class="headerlink" title="生命周期"></a>生命周期</h3><p>每一个产品都具有一个生命周期,从需求阶段——>设计阶段——>开发阶段——>测试阶段——>维护阶段——>死亡阶段</p><h4 id="需求阶段"><a href="#需求阶段" class="headerlink" title="需求阶段"></a>需求阶段</h4><p>这是整个软件开发生命周期中最关键的阶段,在这个阶段,客户需要说明需求、规格、期望以及一些与产品相关的特殊要求。在这个阶段收集到的所有信息对于产品是否符合需求至关重要。</p><h4 id="设计阶段"><a href="#设计阶段" class="headerlink" title="设计阶段"></a>设计阶段</h4><p>设计阶段包括了根据需求阶段对新软件的详细分析。这是系统开发生命周期中的最高优先级阶段,因为系统的逻辑设计需要转化为物理设计。所需阶段的输出是需求事务的集合,设计阶段为实现这些需求提供了方法,所有必须的基本工具的决定,例如编程语言的选择、数据库的选择、硬件的选择、架构的选择,提供了一个平台。软件软件可以在这个平台上运行而没有任何问题。使用生命技术和工具,如数据流图、流程图、决策表。决策树、数据字典和结构化字典用于描述系统设计。</p><h4 id="开发阶段"><a href="#开发阶段" class="headerlink" title="开发阶段"></a>开发阶段</h4><p>在完成需求和设计阶段后,就会将设计实现到软件系统的具体开发中。在这个个阶段,工作可能会划分为一个个小单元,编码由开发人员根据前一阶段讨论的设计开始,并根据需求阶段的要求产生需求结果。前端开发人员开发简单且由吸引力的GUI和必要的接口,以便与后端操作进行交互,后端开发人员根据功能需求进行后端编码。</p><h4 id="测试阶段"><a href="#测试阶段" class="headerlink" title="测试阶段"></a>测试阶段</h4><p>测试是完成软件系统的最后一步,在这里,我们将根据需求阶段中的要求对其进行测试。确认软件是否实际的符合需求。制定测试计划以开始测试,这个测试包含了所有的测试类型。如果测试过程中软件没有按照预期工作,那么就需要向开发提供有关该问题的信息,如果这是一个有效的缺陷或者值得修复,<br>那么它将会被修复,将其替换为新的,对此还需要进行验证测试。</p><h4 id="部署阶段"><a href="#部署阶段" class="headerlink" title="部署阶段"></a>部署阶段</h4><p>当软件测试完成且结果符合预期,并且软件工作中没有余留问题,就可以将他进行交付使用。当客户收到产品时,建议他们优先进行β测试,在β测试中,客户可以要求软件中没有但在需求文档中或其他任何GUI更改中提及的任何更改,以使其更加用户友好。除此之外,如果客户在使用该软件的过程中遇见任何类型的缺陷,它将会通知该软件的开发团队解决问题,如果这是一个严重的问题,那么开发团队需要在短时间内解决问题,如果这是一个不那么严重的问题,那它将会被留置到下个版本,在解决了所有类型的错误和变更后,软件将会被部署到最终用户。</p><h4 id="维护阶段"><a href="#维护阶段" class="headerlink" title="维护阶段"></a>维护阶段</h4><p>维护阶段是SDLC的最后和持久阶段,因为它是一直持续到软件生命周期结束的过程。当客户开始使用软件时,实际问题就已经开始产生,那时需要解决这些问题。这个阶段包含了对硬件以及软件进行更改以维持其运营效率,例如提高性能,增强安全功能以及更具客户的要求和即将到来的时间。这个不时处理产品的过程称之为维护。<br>所有这些都是软件开发生命周期(SDLC)的六个阶段,在这个阶段,软件开发过程发生。所有这些都是强制阶段,没有任何一个开发是不可能的,因为开发在软件的生命周期中持续进行维护”。</p><h4 id="需求分析"><a href="#需求分析" class="headerlink" title="需求分析"></a>需求分析</h4><p>手动测试程序的第一步是需求分析。在此阶段,测试人员分析SDLC(软件开发生命周期)的需求文档,以检查客户所述的要求。在检查要求后,测试人员制定测试计划以检查软件是否满足要求。</p><ul><li>进入条件 - 对于测试计划需求规范的规划,应该提供应用程序体系结构文档和明确定义的验收标准。</li><li>活动行为 - 准备所有要求和查询的列表,并从技术经理/主管,系统架构,业务分析师和客户处获得解决。列出要执行的所有类型的测试(性能,功能和安全性)。列出测试环境详细信息,其中应包含执行测试用例的所有必要工具。</li><li>交付成果 - 列出可测试要求和测试环境详细信息的所有必要测试。</li></ul><h4 id="测试计划"><a href="#测试计划" class="headerlink" title="测试计划"></a>测试计划</h4><p>创建测试计划的创建是STLC的关键阶段,它定义了所有测试策略。测试人员确定整个项目的估计工作量和成本。此阶段在成功完成需求分析阶段后进行。此阶段提供的测试策略和工作量估算文档。成功完成测试计划创建后,可以开始测试用例执行。</p><ul><li>进入条件 - 需求文档活动行为 - 定义目标以及软件的范围。列出测试中涉及的方法。测试过程概述。</li><li>测试环境的解决。准备测试计划和控制程序。角色和责任的确定。列出测试可交付成果,定义风险(如果有)。</li><li>交付成果 - 测试策略文档。测试估算文件是此阶段的交付成果。</li></ul><h4 id="环境设置"><a href="#环境设置" class="headerlink" title="环境设置"></a>环境设置</h4><p>测试环境的设置是一项独立的活动,可以与测试用例开发一起启动。这是手动测试程序的重要部分,因为没有环境测试无法进行。环境设置需要一组必要的软件和硬件来创建测试环境。测试团队不参与设置测试环境,而是创建测试环境的高级开发人员完成。</p><ul><li>进入条件 - 测试策略和测试计划文档。测试用例文档。测试数据。</li><li>活动行为 - 通过分析需求规范来准备软件和硬件列表。在设置测试环境之后,执行测试用例以检查测试环境的准备情况。</li><li>交付成果 - 执行报告。缺陷报告。</li></ul><h4 id="测试用例"><a href="#测试用例" class="headerlink" title="测试用例"></a>测试用例</h4><p>执行测试用例在成功完成测试计划后执行。在此阶段,测试团队启动案例开发和执行活动。测试团队记下详细的测试用例,并在需要时准备测试数据。准备好的测试用例由团队的同行成员或质量保证负责人进行审核。 RTM(需求可追溯性矩阵)也在此阶段准备。需求可跟踪性矩阵是行业级格式,用于跟踪需求。每个测试用例都与需求规范一起映射。可以通过RTM完成向后和向前可追溯性。</p><ul><li>进入条件 - 需求文档。</li><li>活动行为 - 创建测试用例。执行测试用例。根据要求绘制测试用例。</li><li>交付成果 - 测试执行结果。具有缺陷详细说明的功能列表。</li></ul><h4 id="缺陷记录"><a href="#缺陷记录" class="headerlink" title="缺陷记录"></a>缺陷记录</h4><p>测试人员和开发人员根据测试覆盖范围,质量,时间消耗,成本和关键业务目标评估软件的完成标准。此阶段确定了软件的特性和缺点。深入分析测试用例和错误报告,以检测缺陷的类型及其严重性。 缺陷记录分析主要用于根据严重程度和类型找出缺陷分布。如果检测到任何缺陷,则将软件返回给开发团队以修复缺陷,然后在测试的所有方面对软件进行重新测试。 一旦测试周期完全完成,然后测试关闭报告,并准备测试指标。</p><ul><li>进入条件 - 测试用例执行报告。缺陷报告</li><li>活动行为 - 它根据测试覆盖率,质量,时间消耗,成本和关键业务目标评估软件的完成标准。缺陷记录分析通过对类型和严重性进行分类来找出缺陷分布。</li><li>交付成果 - 关闭报告,测试指标</li></ul><h4 id="测试周期"><a href="#测试周期" class="headerlink" title="测试周期"></a>测试周期</h4><p>关闭测试周期结束报告包括与软件设计,开发,测试结果和缺陷报告相关的所有文档。如果存在具有相同规范的软件,此阶段将评估开发策略,测试过程,可能的缺陷,以便将来使用这些实践。</p><ul><li>进入条件 - 所有与软件相关的文档和报告。</li><li>活动行为 - 如果存在具有相同规范的软件,则评估开发策略,测试过程,将来可能存在的缺陷以使用这些实践。</li><li>交付成果 - 测试结束报告。</li></ul><h3 id="质量保证和软件质量控制"><a href="#质量保证和软件质量控制" class="headerlink" title="质量保证和软件质量控制"></a>质量保证和软件质量控制</h3><p>软件质量保证(也称为QA)是一系列任务,用于防止缺陷并确保为特定应用程序设计的技术,方法,方法和过程必须正确实施。这是软件系统开发过程中的持续过程。 应用程序单元的开发按照其开发顺序在质量保证规范下进行检查。 质量保证测试确保了高质量软件的开发,因为它主要关注软件开发过程中的高质量流程,良好的质量管理体系和定期的一致性审核。它是一种管理工具,包括计划和系统的活动和文件,以防止与质量有关的问题。</p><p>软件质量保证的责任不是任何特定的团队,而是开发团队的每个成员的责任。</p><ul><li>软件质量保证可防止缺陷。</li><li>软件质量保证是面向过程的。</li><li>软件质量保证在流程和预防性方面具有前瞻性。</li><li>软件质量保证是一种管理工具。</li><li>每个开发人员都负责软件质量保证。</li></ul><h4 id="软件质量控制"><a href="#软件质量控制" class="headerlink" title="软件质量控制"></a>软件质量控制</h4><p>软件质量控制也称为质量控制,是一系列任务,通过识别缺陷和纠正开发软件中的缺陷来确保软件质量。这是一个被动的过程,此过程的主要目的是在发布软件之前纠正所有类型的缺陷。通过纠正工具消除问题根源(导致质量低下),从而使软件能够满足客户的要求和高质量,从而完成该过程。</p><p>质量控制的责任在于一个特定的团队,称为测试团队,通过验证和纠正工具测试软件的缺陷。</p><ul><li>质量控制提供缺陷识别。</li><li>质量控制是以产品为导向。</li><li>质量控制是一种纠正工具。</li><li>测试团队负责质量控制。</li><li>质量控制是一个反应过程。</li></ul><h4 id="质量保证与质量控制的区别"><a href="#质量保证与质量控制的区别" class="headerlink" title="质量保证与质量控制的区别"></a>质量保证与质量控制的区别</h4><p>软件质量保证与质量控制的区别如下表所示:<br>|项目|质量保证|质量控制|<br>|——|——|——|<br>|定义|质量保证是一组活动,可确保始终保持软件开发过程中使用的过程质量。|QC是一组用于检测已开发软件中的缺陷的活动。|<br>|关注重点|QA的重点是通过关注流程来防止开发软件中的缺陷。|QC的重点是通过关注测试过程来识别开发软件中的缺陷。|<br>|如何做|建立高质量的管理系统,并定期审核开发软件的操作是否符合要求。|通过使用开发软件中的测试技术和工具来检测和消除质量问题元素。|<br>|为什么做|质量保证通过使用包括文档在内的系统活动来确保质量问题的预防。|QC通过使用流程和技术来实现和维护高质量的软件,从而确保识别和消除缺陷。|<br>|面向|质量保证是面向流程的。|QC是面向产品的。|<br>|责任|开发团队的每个成员都负责QA|只有特定的测试团队负责QC|<br>|示例|验证软件流程|检验软件功能和流程|</p>]]></content>
<categories>
<category> 测试 </category>
</categories>
<tags>
<tag> 软件测试 </tag>
</tags>
</entry>
<entry>
<title>Spring 学习笔记</title>
<link href="/posts/4.html"/>
<url>/posts/4.html</url>
<content type="html"><![CDATA[<!-- markdownlint-disable MD025 --><h1 id="Spring开端"><a href="#Spring开端" class="headerlink" title="Spring开端"></a>Spring开端</h1><h2 id="Spring项目的创建"><a href="#Spring项目的创建" class="headerlink" title="Spring项目的创建"></a>Spring项目的创建</h2><p>首先,我们用Maven创建工程并引入<code>spring-context</code>依赖:</p><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag"><<span class="name">dependency</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">groupId</span>></span>org.springframework<span class="tag"></<span class="name">groupId</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">artifactId</span>></span>spring-context<span class="tag"></<span class="name">artifactId</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">version</span>></span>6.0.8<span class="tag"></<span class="name">version</span>></span></span><br><span class="line"><span class="tag"></<span class="name">dependency</span>></span></span><br><span class="line"><span class="tag"><<span class="name">dependency</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">groupId</span>></span>org.springframework<span class="tag"></<span class="name">groupId</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">artifactId</span>></span>spring-webmvc<span class="tag"></<span class="name">artifactId</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">version</span>></span>5.2.6.RELEASE<span class="tag"></<span class="name">version</span>></span></span><br><span class="line"><span class="tag"></<span class="name">dependency</span>></span></span><br></pre></td></tr></table></figure><p>我们先编写一个<code>MailService</code>,用于在用户登录和注册成功后发送邮件通知:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">MailService</span> {</span><br><span class="line"> <span class="keyword">private</span> <span class="type">ZoneId</span> <span class="variable">zoneId</span> <span class="operator">=</span> ZoneId.systemDefault();</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">setZoneId</span><span class="params">(ZoneId zoneId)</span> {</span><br><span class="line"> <span class="built_in">this</span>.zoneId = zoneId;</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> String <span class="title function_">getTime</span><span class="params">()</span> {</span><br><span class="line"> <span class="keyword">return</span> ZonedDateTime.now(<span class="built_in">this</span>.zoneId).format(DateTimeFormatter.ISO_ZONED_DATE_TIME);</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">sendLoginMail</span><span class="params">(User user)</span> {</span><br><span class="line"> System.err.println(String.format(<span class="string">"Hi, %s! You are logged in at %s"</span>, user.getName(), getTime()));</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">sendRegistrationMail</span><span class="params">(User user)</span> {</span><br><span class="line"> System.err.println(String.format(<span class="string">"Welcome, %s!"</span>, user.getName()));</span><br><span class="line"></span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><p>再编写一个<code>UserService</code>,实现用户注册和登录:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">UserService</span> {</span><br><span class="line"> <span class="keyword">private</span> MailService mailService;</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">setMailService</span><span class="params">(MailService mailService)</span> {</span><br><span class="line"> <span class="built_in">this</span>.mailService = mailService;</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">private</span> List<User> users = <span class="keyword">new</span> <span class="title class_">ArrayList</span><>(List.of( <span class="comment">// users:</span></span><br><span class="line"> <span class="keyword">new</span> <span class="title class_">User</span>(<span class="number">1</span>, <span class="string">"[email protected]"</span>, <span class="string">"password"</span>, <span class="string">"Bob"</span>), <span class="comment">// bob</span></span><br><span class="line"> <span class="keyword">new</span> <span class="title class_">User</span>(<span class="number">2</span>, <span class="string">"[email protected]"</span>, <span class="string">"password"</span>, <span class="string">"Alice"</span>), <span class="comment">// alice</span></span><br><span class="line"> <span class="keyword">new</span> <span class="title class_">User</span>(<span class="number">3</span>, <span class="string">"[email protected]"</span>, <span class="string">"password"</span>, <span class="string">"Tom"</span>))); <span class="comment">// tom</span></span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> User <span class="title function_">login</span><span class="params">(String email, String password)</span> {</span><br><span class="line"> <span class="keyword">for</span> (User user : users) {</span><br><span class="line"> <span class="keyword">if</span> (user.getEmail().equalsIgnoreCase(email) && user.getPassword().equals(password)) {</span><br><span class="line"> mailService.sendLoginMail(user);</span><br><span class="line"> <span class="keyword">return</span> user;</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line"> <span class="keyword">throw</span> <span class="keyword">new</span> <span class="title class_">RuntimeException</span>(<span class="string">"login failed."</span>);</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> User <span class="title function_">getUser</span><span class="params">(<span class="type">long</span> id)</span> {</span><br><span class="line"> <span class="keyword">return</span> <span class="built_in">this</span>.users.stream().filter(user -> user.getId() == id).findFirst().orElseThrow();</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="keyword">public</span> User <span class="title function_">register</span><span class="params">(String email, String password, String name)</span> {</span><br><span class="line"> users.forEach((user) -> {</span><br><span class="line"> <span class="keyword">if</span> (user.getEmail().equalsIgnoreCase(email)) {</span><br><span class="line"> <span class="keyword">throw</span> <span class="keyword">new</span> <span class="title class_">RuntimeException</span>(<span class="string">"email exist."</span>);</span><br><span class="line"> }</span><br><span class="line"> });</span><br><span class="line"> <span class="type">User</span> <span class="variable">user</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">User</span>(users.stream().mapToLong(u -> u.getId()).max().getAsLong() + <span class="number">1</span>, email, password, name);</span><br><span class="line"> users.add(user);</span><br><span class="line"> mailService.sendRegistrationMail(user);</span><br><span class="line"> <span class="keyword">return</span> user;</span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><p>注意到<code>UserService</code>通过<code>setMailService()</code>注入了一个<code>MailService</code>。</p><p>然后,我们需要编写一个特定的<code>application.xml</code>配置文件,告诉Spring的IoC容器应该如何创建并组装Bean:</p><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta"><?xml version=<span class="string">"1.0"</span> encoding=<span class="string">"UTF-8"</span>?></span></span><br><span class="line"><span class="tag"><<span class="name">beans</span> <span class="attr">xmlns</span>=<span class="string">"http://www.springframework.org/schema/beans"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xmlns:xsi</span>=<span class="string">"http://www.w3.org/2001/XMLSchema-instance"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xsi:schemaLocation</span>=<span class="string">"http://www.springframework.org/schema/beans</span></span></span><br><span class="line"><span class="string"><span class="tag"> https://www.springframework.org/schema/beans/spring-beans.xsd"</span>></span></span><br><span class="line"></span><br><span class="line"> <span class="tag"><<span class="name">bean</span> <span class="attr">id</span>=<span class="string">"userService"</span> <span class="attr">class</span>=<span class="string">"com.itranswarp.learnjava.service.UserService"</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">property</span> <span class="attr">name</span>=<span class="string">"mailService"</span> <span class="attr">ref</span>=<span class="string">"mailService"</span> /></span></span><br><span class="line"> <span class="tag"></<span class="name">bean</span>></span></span><br><span class="line"></span><br><span class="line"> <span class="tag"><<span class="name">bean</span> <span class="attr">id</span>=<span class="string">"mailService"</span> <span class="attr">class</span>=<span class="string">"com.itranswarp.learnjava.service.MailService"</span> /></span></span><br><span class="line"><span class="tag"></<span class="name">beans</span>></span></span><br></pre></td></tr></table></figure><ul><li>每个<code><bean ...></code>都有一个<code>id</code>标识,相当于Bean的唯一ID;</li><li>在<code>userService</code>Bean中,通过<code><property name="..." ref="..." /></code>注入了另一个Bean;</li><li>Bean的顺序不重要,Spring根据依赖关系会自动正确初始化。</li></ul><p>把上述XML配置文件用Java代码写出来,就像这样:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="type">UserService</span> <span class="variable">userService</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">UserService</span>();</span><br><span class="line"><span class="type">MailService</span> <span class="variable">mailService</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">MailService</span>();</span><br><span class="line">userService.setMailService(mailService);</span><br></pre></td></tr></table></figure><p>只不过Spring容器是通过读取XML文件后使用反射完成的。</p><p>如果注入的不是Bean,而是<code>boolean</code>、<code>int</code>、<code>String</code>这样的数据类型,则通过<code>value</code>注入,例如,创建一个<code>HikariDataSource</code>:</p><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag"><<span class="name">bean</span> <span class="attr">id</span>=<span class="string">"dataSource"</span> <span class="attr">class</span>=<span class="string">"com.zaxxer.hikari.HikariDataSource"</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">property</span> <span class="attr">name</span>=<span class="string">"jdbcUrl"</span> <span class="attr">value</span>=<span class="string">"jdbc:mysql://localhost:3306/test"</span> /></span></span><br><span class="line"> <span class="tag"><<span class="name">property</span> <span class="attr">name</span>=<span class="string">"username"</span> <span class="attr">value</span>=<span class="string">"root"</span> /></span></span><br><span class="line"> <span class="tag"><<span class="name">property</span> <span class="attr">name</span>=<span class="string">"password"</span> <span class="attr">value</span>=<span class="string">"password"</span> /></span></span><br><span class="line"> <span class="tag"><<span class="name">property</span> <span class="attr">name</span>=<span class="string">"maximumPoolSize"</span> <span class="attr">value</span>=<span class="string">"10"</span> /></span></span><br><span class="line"> <span class="tag"><<span class="name">property</span> <span class="attr">name</span>=<span class="string">"autoCommit"</span> <span class="attr">value</span>=<span class="string">"true"</span> /></span></span><br><span class="line"><span class="tag"></<span class="name">bean</span>></span></span><br></pre></td></tr></table></figure><p>最后一步,我们需要创建一个Spring的IoC容器实例,然后加载配置文件,让Spring容器为我们创建并装配好配置文件中指定的所有Bean,这只需要一行代码:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// 获取Bean:</span></span><br><span class="line"><span class="type">UserService</span> <span class="variable">userService</span> <span class="operator">=</span> context.getBean(UserService.class);</span><br><span class="line"><span class="comment">// 正常调用:</span></span><br><span class="line"><span class="type">User</span> <span class="variable">user</span> <span class="operator">=</span> userService.login(<span class="string">"[email protected]"</span>, <span class="string">"password"</span>);</span><br></pre></td></tr></table></figure><p>完整的<code>main()</code>方法如下:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">Main</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> {</span><br><span class="line"> <span class="type">ApplicationContext</span> <span class="variable">context</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">ClassPathXmlApplicationContext</span>(<span class="string">"application.xml"</span>);</span><br><span class="line"> <span class="type">UserService</span> <span class="variable">userService</span> <span class="operator">=</span> context.getBean(UserService.class);</span><br><span class="line"> <span class="type">User</span> <span class="variable">user</span> <span class="operator">=</span> userService.login(<span class="string">"[email protected]"</span>, <span class="string">"password"</span>);</span><br><span class="line"> System.out.println(user.getName());</span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><h3 id="ApplicationContext"><a href="#ApplicationContext" class="headerlink" title="ApplicationContext"></a>ApplicationContext</h3><p>我们从创建Spring容器的代码:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="type">ApplicationContext</span> <span class="variable">context</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">ClassPathXmlApplicationContext</span>(<span class="string">"application.xml"</span>);</span><br></pre></td></tr></table></figure><p>可以看到,Spring容器就是<code>ApplicationContext</code>,它是一个接口,有很多实现类,这里我们选择<code>ClassPathXmlApplicationContext</code>,表示它会自动从classpath中查找指定的XML配置文件。</p><p>获得了<code>ApplicationContext</code>的实例,就获得了IoC容器的引用。从<code>ApplicationContext</code>中我们可以根据Bean的ID获取Bean,但更多的时候我们根据Bean的类型获取Bean的引用:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="type">UserService</span> <span class="variable">userService</span> <span class="operator">=</span> context.getBean(UserService.class);</span><br></pre></td></tr></table></figure><p>Spring还提供另一种IoC容器叫<code>BeanFactory</code>,使用方式和<code>ApplicationContext</code>类似:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="type">BeanFactory</span> <span class="variable">factory</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">XmlBeanFactory</span>(<span class="keyword">new</span> <span class="title class_">ClassPathResource</span>(<span class="string">"application.xml"</span>));</span><br><span class="line"><span class="type">MailService</span> <span class="variable">mailService</span> <span class="operator">=</span> factory.getBean(MailService.class);</span><br></pre></td></tr></table></figure><p><code>BeanFactory</code>和<code>ApplicationContext</code>的区别在于,<code>BeanFactory</code>的实现是按需创建,即第一次获取Bean时才创建这个Bean,而<code>ApplicationContext</code>会一次性创建所有的Bean。实际上,<code>ApplicationContext</code>接口是从<code>BeanFactory</code>接口继承而来的,并且,<code>ApplicationContext</code>提供了一些额外的功能,包括国际化支持、事件和通知机制等。通常情况下,我们总是使用<code>ApplicationContext</code>,很少会考虑使用<code>BeanFactory</code>。</p><h3 id="小结"><a href="#小结" class="headerlink" title="小结"></a>小结</h3><p>Spring的IoC容器接口是<code>ApplicationContext</code>,并提供了多种实现类;</p><p>通过XML配置文件创建IoC容器时,使用<code>ClassPathXmlApplicationContext</code>;</p><p>持有IoC容器后,通过<code>getBean()</code>方法获取Bean的引用。</p><h1 id="关于原型对象"><a href="#关于原型对象" class="headerlink" title="关于原型对象"></a>关于原型对象</h1><p>Spring默认使用单例模式(单例模式,整个生命周期都只有这一个对象,对象的唯一。),但是如果我们要让一个对象每次被实例化时产生的都是一个新对象,那我们就需要设置Bean的scope=”prototype”</p><h1 id="Spring自动装配"><a href="#Spring自动装配" class="headerlink" title="Spring自动装配"></a>Spring自动装配</h1><p>属性名:AutoWire 属性值:【ByName,ByType,constructor,default,no】</p><p>ByName:自动在容器上下文中寻找,和自己对象Set方法后面的值对应的BeanID,需要保证所有Bean的ID唯一性,并且这个Bean需要和自动注入的Set方法的值一致!</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><bean id=<span class="string">"people"</span> class=<span class="string">"People"</span> autowire=<span class="string">"byName"</span>></span><br><span class="line"> <property name=<span class="string">"name"</span> value=<span class="string">"王某"</span>/></span><br><span class="line"> </bean></span><br></pre></td></tr></table></figure><p>ByType:自动在容器上下文中寻找,和自己对象属性类型值相同的Bean,这时,我们可以取消ID属性,因为装配过程不再依赖于ID。需要保证所有Bean的Class唯一性,并且这个Bean需要和自动注入的属性的类型一致!</p><h1 id="使用注解实现自动装配"><a href="#使用注解实现自动装配" class="headerlink" title="使用注解实现自动装配"></a>使用注解实现自动装配</h1><h2 id="关于注解"><a href="#关于注解" class="headerlink" title="关于注解"></a>关于注解</h2><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@Autowired</span>:根据属性类型进行自动装配,若接口不止一个实现,则按照属性名(因为可以不加set)进行匹配bean</span><br><span class="line"><span class="meta">@Qualifier</span>:必须配合Autowired使用,可以帮助指定实现类id</span><br><span class="line"><span class="meta">@Resource</span>:可以根据类型注入,可以根据名称注入</span><br><span class="line"><span class="meta">@Value</span>:注入普通类型属性</span><br><span class="line"><span class="meta">@Autowired</span>:可以根据类型注入,可以根据名称注入(默认优先进行byType装配)</span><br><span class="line">若接口不止一个实现,则按照属性名(因为可以不加set)进行匹配bean</span><br><span class="line">创建实体类对象,在实体类中对象类型属性上或set方法上加上该注解。</span><br><span class="line">加入该注解后,该属性可以不需要添加set方法</span><br><span class="line"><span class="meta">@Qualifier</span>:若Autowired按属性名匹配,则可以配合<span class="meta">@Qualifier</span> 注解指定实现类id</span><br><span class="line"><span class="meta">@Resource</span>: 可以根据类型注入,可以根据名称注入(默认优先进行byName装配)</span><br><span class="line">如果同时指定了name和type,则从Spring上下文中找到唯一匹配的bean进行装配,找不到则抛出异常</span><br><span class="line">如果指定了name,则从上下文中查找名称(id)匹配的bean进行装配,找不到则抛出异常</span><br><span class="line">如果指定了type,则从上下文中找到类型匹配的唯一bean进行装配,找不到或者找到多个,都会抛出异常</span><br><span class="line">如果既没有指定name,又没有指定type,则自动按照byName方式进行装配;如果没有匹配,则回退为一个原始类型进行匹配,如果匹配则自动装配;</span><br><span class="line"><span class="meta">@Value</span>:注入普通类型属性</span><br><span class="line">代替了<property name=<span class="string">"..."</span> value=<span class="string">"..."</span>/> 的繁琐操作。</span><br></pre></td></tr></table></figure><p>使用注解须知:</p><p>1.导入约束 context约束<br><!-- markdownlint-disable MD036 --><br><strong>2.配置注解的支持 context:annotation-config</strong></p><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta"><?xml version=<span class="string">"1.0"</span> encoding=<span class="string">"UTF-8"</span>?></span></span><br><span class="line"><span class="tag"><<span class="name">beans</span> <span class="attr">xmlns</span>=<span class="string">"http://www.springframework.org/schema/beans"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xmlns:xsi</span>=<span class="string">"http://www.w3.org/2001/XMLSchema-instance"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xmlns:context</span>=<span class="string">"http://www.springframework.org/schema/context"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xsi:schemaLocation</span>=<span class="string">"http://www.springframework.org/schema/beans</span></span></span><br><span class="line"><span class="string"><span class="tag"> https://www.springframework.org/schema/beans/spring-beans.xsd</span></span></span><br><span class="line"><span class="string"><span class="tag"> http://www.springframework.org/schema/context</span></span></span><br><span class="line"><span class="string"><span class="tag"> https://www.springframework.org/schema/context/spring-context.xsd"</span>></span></span><br><span class="line"> <span class="tag"><<span class="name">context:annotation-config</span>/></span></span><br><span class="line"></span><br><span class="line"><span class="tag"></<span class="name">beans</span>></span></span><br></pre></td></tr></table></figure><p>@Autowired</p><p>直接在属性上使用即可!也可以在set上使用!</p><p>使用Autowired我们可以不用再编写set方法,前提是这个自动装配的属性在IOC(spring)容器中存在,且符合名字ByName!</p><p>科普:</p><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">@Nullable 字段标记了这个注解,说明这个字段可以为null;</span><br></pre></td></tr></table></figure><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="literal">false</span>值可以为<span class="literal">null</span></span><br><span class="line"><span class="meta">@Autowired(required = false)</span></span><br><span class="line">另外还有<span class="meta">@Resource</span>注解(自动通过名字,类型,注入)</span><br><span class="line"><span class="meta">@Component</span>(组件,放在类上,说明这个类被Spring管理;了,这就是Bean)</span><br><span class="line"></span><br></pre></td></tr></table></figure><h2 id="Component衍生注解"><a href="#Component衍生注解" class="headerlink" title="@Component衍生注解"></a>@Component衍生注解</h2><p>@Component拥有几个衍生注解,在之后的SpringMVC中会进行三层架构分层</p><p>dao(@Repository)</p><p>Service(@Service)</p><p>controller(@Controller)</p><p>四个注解功能是一样的,都是将某个类注册到Spring中,装配Bean</p><h3 id="自动装配"><a href="#自动装配" class="headerlink" title="自动装配"></a>自动装配</h3><figure class="highlight text"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">@Autowired不能唯一自动装配注解:自动装配通过类型,名字</span><br><span class="line">如果@Autowired不能唯一自动装配注解,那么就需要@Qualifier(value="")</span><br><span class="line"></span><br></pre></td></tr></table></figure><h3 id="作用域"><a href="#作用域" class="headerlink" title="作用域"></a>作用域</h3><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">@Component</span></span><br><span class="line"><span class="meta">@Scope("prototype")</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">User</span> {</span><br><span class="line"> <span class="meta">@Value("小王")</span></span><br><span class="line"> <span class="keyword">public</span> String name;</span><br><span class="line"></span><br><span class="line">}</span><br></pre></td></tr></table></figure><h1 id="完全使用Java方式配置Spring"><a href="#完全使用Java方式配置Spring" class="headerlink" title="完全使用Java方式配置Spring"></a>完全使用Java方式配置Spring</h1><p>配置文件:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> top.yuanfangwa.Config;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> org.springframework.context.annotation.Bean;</span><br><span class="line"><span class="keyword">import</span> org.springframework.context.annotation.ComponentScan;</span><br><span class="line"><span class="keyword">import</span> org.springframework.context.annotation.Configuration;</span><br><span class="line"><span class="keyword">import</span> top.yuanfangwa.pojo.USer;</span><br><span class="line"></span><br><span class="line"><span class="comment">/**</span></span><br><span class="line"><span class="comment"> * <span class="doctag">@Author</span>:无知啊</span></span><br><span class="line"><span class="comment"> * <span class="doctag">@ProJect</span>_Name:SpringDemo</span></span><br><span class="line"><span class="comment"> * <span class="doctag">@Date</span>:2022/3/1214:20</span></span><br><span class="line"><span class="comment"> * <span class="doctag">@Description</span>:</span></span><br><span class="line"><span class="comment"> * <span class="doctag">@Since</span> version:1.0</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="comment">//这个也会被Spring容器接管,因为他本身也是一个Component,</span></span><br><span class="line"><span class="comment">// @Configuration代表着这是一个配置类,就和之前的Beans.xml是一样的</span></span><br><span class="line"><span class="meta">@Configuration</span></span><br><span class="line"><span class="meta">@ComponentScan("top.yuanfangwa.pojo")</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">Config</span> {</span><br><span class="line"><span class="comment">//注册一个Bean就相当于我们之前写的一个Bean标签</span></span><br><span class="line"><span class="comment">//方法名就相当于之前Bean标签的ID属性</span></span><br><span class="line"><span class="comment">// 返回值就相当于之前的class属性</span></span><br><span class="line"> <span class="meta">@Bean</span></span><br><span class="line"> <span class="keyword">public</span> USer <span class="title function_">getBean</span><span class="params">()</span> {</span><br><span class="line"> <span class="keyword">return</span> <span class="keyword">new</span> <span class="title class_">USer</span>();<span class="comment">//就是要返回的Bean</span></span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></span><br></pre></td></tr></table></figure><p>测试:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> org.springframework.context.ApplicationContext;</span><br><span class="line"><span class="keyword">import</span> org.springframework.context.annotation.AnnotationConfigApplicationContext;</span><br><span class="line"><span class="keyword">import</span> top.yuanfangwa.Config.Config;</span><br><span class="line"><span class="keyword">import</span> top.yuanfangwa.pojo.USer;</span><br><span class="line"></span><br><span class="line"><span class="comment">/**</span></span><br><span class="line"><span class="comment"> * <span class="doctag">@Author</span>:无知啊</span></span><br><span class="line"><span class="comment"> * <span class="doctag">@ProJect</span>_Name:SpringDemo</span></span><br><span class="line"><span class="comment"> * <span class="doctag">@Date</span>:2022/3/1214:22</span></span><br><span class="line"><span class="comment"> * <span class="doctag">@Description</span>:</span></span><br><span class="line"><span class="comment"> * <span class="doctag">@Since</span> version:1.0</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">Mytset</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> {</span><br><span class="line"> <span class="type">ApplicationContext</span> <span class="variable">Context</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">AnnotationConfigApplicationContext</span>(Config.class);</span><br><span class="line"> <span class="type">USer</span> <span class="variable">user</span> <span class="operator">=</span> (USer) Context.getBean(<span class="string">"getBean"</span>);</span><br><span class="line"> System.out.println(user.getName());</span><br><span class="line"></span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></span><br></pre></td></tr></table></figure><p>这样的配置在Spring boot中随处可见</p><h1 id="代理模式"><a href="#代理模式" class="headerlink" title="代理模式"></a>代理模式</h1><p>代理模式可以使得原本的操作变得纯粹</p><h1 id="aop约束"><a href="#aop约束" class="headerlink" title="aop约束"></a>aop约束</h1><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta"><?xml version=<span class="string">"1.0"</span> encoding=<span class="string">"UTF-8"</span>?></span></span><br><span class="line"><span class="tag"><<span class="name">beans</span> <span class="attr">xmlns</span>=<span class="string">"http://www.springframework.org/schema/beans"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xmlns:xsi</span>=<span class="string">"http://www.w3.org/2001/XMLSchema-instance"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xmlns:aop</span>=<span class="string">"http://www.springframework.org/schema/aop"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xsi:schemaLocation</span>=<span class="string">"http://www.springframework.org/schema/beans</span></span></span><br><span class="line"><span class="string"><span class="tag"> https://www.springframework.org/schema/beans/spring-beans.xsd</span></span></span><br><span class="line"><span class="string"><span class="tag"> http://www.springframework.org/schema/aop</span></span></span><br><span class="line"><span class="string"><span class="tag"> https://www.springframework.org/schema/aop/spring-aop.xsd"</span>></span></span><br><span class="line"><span class="tag"></<span class="name">beans</span>></span></span><br></pre></td></tr></table></figure><h1 id="Aop-表达式"><a href="#Aop-表达式" class="headerlink" title="Aop 表达式"></a>Aop 表达式</h1><p>Aop中expression表达式的表示方法</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br></pre></td><td class="code"><pre><span class="line">常见的切面表达式</span><br><span class="line"><span class="number">1</span> 所有公有方法的执行</span><br><span class="line"></span><br><span class="line">execution(<span class="keyword">public</span> * *(..))</span><br><span class="line"></span><br><span class="line"><span class="number">2</span> 所有以set开头的公有方法的执行</span><br><span class="line"></span><br><span class="line">execution(* set*(..))</span><br><span class="line"></span><br><span class="line"><span class="number">3</span> AccountService接口下的所有方法的执行</span><br><span class="line"></span><br><span class="line">execution(* com.LightseaBlue.service.AccountService.*(..))</span><br><span class="line"></span><br><span class="line"><span class="number">4</span> com.LightseaBlue.service包下的所有方法的执行</span><br><span class="line"></span><br><span class="line">execution(* com.LightseaBlue.service.*.*(..))</span><br><span class="line"></span><br><span class="line"><span class="number">5</span> com.LightseaBlue.service包及其子包下的所有方法的执行</span><br><span class="line"></span><br><span class="line">execution(* com.LightseaBlue.service..*.*(..))</span><br><span class="line"></span><br><span class="line"><span class="number">6</span> 匹配com.LightseaBlue.service包下的所有类的所有方法(不含子包)</span><br><span class="line"></span><br><span class="line">within(com.LightseaBlue.service.*)</span><br><span class="line"></span><br><span class="line"><span class="number">7</span> com.LightseaBlue.service包和子包的所有方法</span><br><span class="line"></span><br><span class="line">within(com.LightseaBlue.service..*)</span><br><span class="line"></span><br><span class="line"><span class="number">8</span> 匹配AccountService的代理类(不支持通配符)</span><br><span class="line"></span><br><span class="line"><span class="built_in">this</span>(com.LightseaBlue.service.AccountService)</span><br></pre></td></tr></table></figure><h1 id="spring整合Mybatis"><a href="#spring整合Mybatis" class="headerlink" title="spring整合Mybatis"></a>spring整合Mybatis</h1><!-- markdownlint-disable MD001 --><h3 id="约束"><a href="#约束" class="headerlink" title="约束"></a>约束</h3><figure class="highlight xml"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="tag"><<span class="name">beans</span> <span class="attr">xmlns</span>=<span class="string">"http://www.springframework.org/schema/beans"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xmlns:xsi</span>=<span class="string">"http://www.w3.org/2001/XMLSchema-instance"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xmlns:aop</span>=<span class="string">"http://www.springframework.org/schema/aop"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xmlns:tx</span>=<span class="string">"http://www.springframework.org/schema/tx"</span></span></span><br><span class="line"><span class="tag"> <span class="attr">xsi:schemaLocation</span>=<span class="string">"http://www.springframework.org/schema/beans</span></span></span><br><span class="line"><span class="string"><span class="tag">https://www.springframework.org/schema/beans/spring-beans.xsd</span></span></span><br><span class="line"><span class="string"><span class="tag">http://www.springframework.org/schema/aop</span></span></span><br><span class="line"><span class="string"><span class="tag">https://www.springframework.org/schema/aop/spring-aop.xsd</span></span></span><br><span class="line"><span class="string"><span class="tag"> http://www.springframework.org/schema/tx</span></span></span><br><span class="line"><span class="string"><span class="tag"> https://www.springframework.org/schema/aop/spring-tx.xsd"</span>></span></span><br><span class="line"><span class="tag"></<span class="name">beans</span>></span></span><br></pre></td></tr></table></figure><p>总体来说,Spring负责了我们原本所需要负责的所有事情,我们只需要去设定实体类以及注入所需要的信息。</p><h1 id="spring-事务"><a href="#spring-事务" class="headerlink" title="spring 事务"></a>spring 事务</h1><p>默认情况下只会回滚<code>RuntimeException</code>(运行时异常)和<code>Error</code>(错误),对于普通的 Exception(非运行时异常),它不会回滚。回滚生效也是有范围的,需处于public</p>]]></content>
<categories>
<category> 编程 </category>
<category> Java </category>
</categories>
<tags>
<tag> Spring </tag>
</tags>
</entry>
<entry>
<title>Java基础!</title>
<link href="/posts/2.html"/>
<url>/posts/2.html</url>
<content type="html"><![CDATA[<h2 id="一、修饰符"><a href="#一、修饰符" class="headerlink" title="一、修饰符"></a>一、修饰符</h2><h3 id="1、final"><a href="#1、final" class="headerlink" title="1、final"></a>1、<strong>final</strong></h3><h4 id="final关键字是最终的意思,可以修饰成员方法,成员变量,类"><a href="#final关键字是最终的意思,可以修饰成员方法,成员变量,类" class="headerlink" title="final关键字是最终的意思,可以修饰成员方法,成员变量,类"></a>final关键字是最终的意思,可以修饰成员方法,成员变量,类</h4><p><strong>final</strong>修饰的特点:</p><ul><li>修饰方法:表面该方法是最终的方法,<strong><em>不能被重写</em></strong></li><li>修饰变量:表明该变量是常量,<strong><em>不能再次被赋值</em></strong></li><li>修饰类:表明该类是最终类,<strong><em>不能被继承</em></strong></li></ul><h4 id="final修饰局部变量"><a href="#final修饰局部变量" class="headerlink" title="final修饰局部变量"></a><strong>final</strong>修饰局部变量</h4><ul><li>变量是基本数据类型:final修饰指的是基本数据类型的<strong><em>数据值</em></strong>不能发生改变</li><li>变量是引用数据类型:final修饰指的是音乐数据类型的<strong><em>地址值</em></strong>不能发生改变,但是地址值里面的内容是可以发生改变的</li></ul><h4 id="2、static"><a href="#2、static" class="headerlink" title="2、static"></a>2、static</h4><h4 id="static关键字是静态的意思,可以修饰成员方法,成员变量"><a href="#static关键字是静态的意思,可以修饰成员方法,成员变量" class="headerlink" title="static关键字是静态的意思,可以修饰成员方法,成员变量"></a><strong><em>static</em></strong>关键字是静态的意思,可以修饰成员方法,成员变量</h4><p><strong><em>static</em></strong>修饰的特点:</p><ul><li>该类的所有对象共享</li></ul><p>这也是判断是否使用静态关键字的条件</p><ul><li>可以通过类名调用</li></ul><p>也可以通过对象名调用</p><p><strong><em>static</em></strong>访问特点:</p><p>非静态的成员方法:(没有被static修饰符修饰过的成员方法)</p><ul><li>能访问静态的成员变量</li><li>能访问非静态的成员变量</li><li>能访问静态的成员方法</li><li>能访问非静态的成员方法</li></ul><p>静态的成员方法(被static修饰符修饰过的成员方法)</p><ul><li>能访问静态的成员变量</li><li>能访问静态的成员方法</li></ul><p><strong>总结:静态成员方法只能访问静态成员</strong></p><h1 id="二、多态"><a href="#二、多态" class="headerlink" title="二、多态"></a>二、多态</h1><h2 id="1-1-多态概述"><a href="#1-1-多态概述" class="headerlink" title="1.1 多态概述"></a>1.1 多态概述</h2><p>同一个对象,在不同时刻表现出来的不同形态</p><p>例:猫</p><p>可以说猫是猫:<strong>猫 cat = new 猫();</strong></p><p>也可以说猫是动物:<strong>动物 animal = new 猫();</strong></p><p>这里猫在不同时刻表现出来了不同的形态,这就是多态</p><p>多态的前提和体现</p><ul><li><p>有继承/实现关系</p></li><li><p>有方法重写</p></li><li><p>有父类引用指向子类</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="type">Animal</span> <span class="variable">animal</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">Cat</span>(); <span class="comment">//这就是父类引用指向子类</span></span><br></pre></td></tr></table></figure></li></ul><h3 id="1-2-多态中成员访问特点"><a href="#1-2-多态中成员访问特点" class="headerlink" title="1.2 多态中成员访问特点"></a>1.2 多态中成员访问特点</h3><ul><li><strong>成员变量:</strong>编译看左边,运行看左边</li><li><strong>成员方法:</strong>编译看左边,运行看右边</li></ul><p>为什么成员变量和成员方法的访问不一样?</p><ul><li>因为成员方法有重写,而成员变量没有</li></ul><h4 id="1-3-多态的好处和弊端"><a href="#1-3-多态的好处和弊端" class="headerlink" title="1.3 多态的好处和弊端"></a>1.3 多态的好处和弊端</h4><ul><li>多态的好处:提高程序的拓展性</li></ul><p>具体体现:定义方法的时候,使用父类型作为参数,将来在使用的时候,使用具体的子类型参与操作</p><ul><li>多态的弊端:不能使用子类的特有功能(不能使用子类的成员方法)</li></ul><h4 id="1-4-多态中的转型"><a href="#1-4-多态中的转型" class="headerlink" title="1.4 多态中的转型"></a>1.4 多态中的转型</h4><ul><li>向上转型</li></ul><p>从子到父</p><p>父类引用指向子类对象</p><ul><li>向下转型</li></ul><p>从父到子</p><p>父类引用转为子类对象</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">AnimalDemo</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> {</span><br><span class="line"> <span class="comment">//多态</span></span><br><span class="line"> <span class="type">Animal</span> <span class="variable">a</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">Cat</span>(); <span class="comment">// 向上转型</span></span><br><span class="line"> a.eat();</span><br><span class="line"></span><br><span class="line"> <span class="comment">// 向下转型</span></span><br><span class="line"> <span class="type">Cat</span> <span class="variable">c</span> <span class="operator">=</span> (Cat)a;</span><br><span class="line"> c.eat();</span><br><span class="line"> c.playGame();</span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><h1 id="三、抽象类"><a href="#三、抽象类" class="headerlink" title="三、抽象类"></a>三、抽象类</h1><h2 id="1-1-抽象类概述"><a href="#1-1-抽象类概述" class="headerlink" title="1.1 抽象类概述"></a>1.1 抽象类概述</h2><p> 在Java中,一个<strong>没用方法体</strong>的方法应该定义为<strong>抽象方法</strong>,而类中如果有<strong>抽象方法</strong>,则该类必须定义为<strong>抽象类</strong></p><h2 id="1-2-抽象类的特点"><a href="#1-2-抽象类的特点" class="headerlink" title="1.2 抽象类的特点"></a>1.2 抽象类的特点</h2><ul><li><p>抽象类和抽象方法必须用<strong>abstract</strong>关键字修饰</p><p> public <strong>abstract</strong>class 类名{}</p><p> public <strong>abstract</strong>void eat();</p></li><li><p>抽象类中不一定有抽象方法,有抽象方法的类一定是抽象类</p></li><li><p>抽象类不能实例化</p></li></ul><p> 可以参照抽象的方式,通过子类对象实例化,这叫抽象类多态</p><ul><li>抽象类的子类</li></ul><p> 要么重写抽象类中的所有抽象方法</p><p> 要么是抽象类(把子类也定义成抽象类)</p><h2 id="1-3-抽象类的成员特点"><a href="#1-3-抽象类的成员特点" class="headerlink" title="1.3 抽象类的成员特点"></a>1.3 抽象类的成员特点</h2><ul><li>成员变量</li></ul><p> 可以是变量</p><p> 也可以是常量</p><ul><li>构造方法</li></ul><p> 有构造方法,但是不能实例化</p><p> 构造方法的作用? 用于子类访问父类数据的初始化</p><ul><li>成员方法</li></ul><p> 可以有抽象方法:限定子类必须完成某些动作</p><p> 也可以有非抽象方法:提高代码复用性</p><h1 id="四、接口"><a href="#四、接口" class="headerlink" title="四、接口"></a>四、接口</h1><h2 id="1-1-接口概述"><a href="#1-1-接口概述" class="headerlink" title="1.1 接口概述"></a>1.1 接口概述</h2><p> 接口就是一种<strong>公共的规范标准</strong>,只要符合规范标准,都可以通用Java中的接口,更多的体现在<strong>对行为的抽象</strong></p><h2 id="1-2-接口的特点"><a href="#1-2-接口的特点" class="headerlink" title="1.2 接口的特点"></a>1.2 接口的特点</h2><ul><li>接口用关键字interface修饰</li></ul><p> public <strong>interface</strong> 接口名{}</p><ul><li>类实现接口用implements表示</li></ul><p> public class 类名 implements 接口名 {}</p><ul><li>接口不能实例化</li></ul><p> 接口实例化按照多态的方式,通过实现类对象实例化,这叫接口多态</p><p> 多态的形式:具体类多态,<strong>抽象类多态,接口多态</strong></p><p> 多态的前提:有继承或者实现关系;有方法重写;有父(类/接口)引用指向(子/实现)类对象</p><ul><li>接口的实现类</li></ul><p> 要么重写接口中的所有抽象方法</p><p> 要么是抽象类</p><h2 id="1-3-接口的成员特点"><a href="#1-3-接口的成员特点" class="headerlink" title="1.3 接口的成员特点"></a>1.3 接口的成员特点</h2><ul><li>成员变量</li></ul><p> 只能是常量</p><p> 默认修饰符:<strong>public static final</strong></p><ul><li>构造方法</li></ul><p> 接口没用构造方法,因为接口主要是对行为进行抽象的,没用具体存在</p><p> 一个类如果没用父类,默认继承Object类</p><ul><li>成员方法</li></ul><p> 只能是抽象方法</p><p> 默认修饰符:public abstract</p><h2 id="1-4-类和接口的关系"><a href="#1-4-类和接口的关系" class="headerlink" title="1.4 类和接口的关系"></a>1.4 类和接口的关系</h2><ul><li>类和类的关系</li></ul><p> 继承关系,只能单继承,但是可以多层继承</p><ul><li>类和接口的关系</li></ul><p> 实现关系,可以单实现,也可以多实现,还可以在继承一个类的同时实现多个接口</p><ul><li>接口和接口的关系</li></ul><p> 继承关系,可以单继承,也可以多继承</p><h2 id="1-5-抽象类和接口的区别"><a href="#1-5-抽象类和接口的区别" class="headerlink" title="1.5 抽象类和接口的区别"></a>1.5 抽象类和接口的区别</h2><ul><li>成员区别</li></ul><p> 抽象类 变量,常量;有构造方法;由抽象方法;也有非抽象方法</p><p> 接口 常量,抽象方法</p><ul><li>关系区别</li></ul><p> 类与类 继承,单继承</p><p> 类与接口 实现,可以单实现,也可以多实现</p><p> 接口与接口 继承,单实现,多继承</p><ul><li>设计理念区别</li></ul><p> 抽象类 对类抽象,包括属性、行为</p><p> 接口 对行为抽象,主要是行为</p><h1 id="五、内部类"><a href="#五、内部类" class="headerlink" title="五、内部类"></a>五、内部类</h1><h2 id="1-1-内部类概述"><a href="#1-1-内部类概述" class="headerlink" title="1.1 内部类概述"></a>1.1 内部类概述</h2><p> 内部类:就是在一个类中定义一个类。 例:在一个类A的内部定义一个类B,类B就是内部类</p><p> 内部类定义格式</p><ul><li>格式</li></ul><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> class 类名 {</span><br><span class="line"> 修饰符 class 类名 {</span><br><span class="line"></span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><ul><li>范例</li></ul><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">Outer</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">Inner</span> {</span><br><span class="line"></span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><blockquote><p>内部类访问特点</p></blockquote><ul><li>内部类可以直接访问外部类的成员,包括私有</li><li>外部类要访问内部类的成员,必须创建对象</li></ul><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">Outer</span> {</span><br><span class="line"> <span class="comment">// 创建内部类</span></span><br><span class="line"> <span class="keyword">private</span> <span class="keyword">class</span> <span class="title class_">Inner</span> {</span><br><span class="line"> <span class="keyword">void</span> <span class="title function_">show</span><span class="params">()</span> {</span><br><span class="line"> System.out.println(age);</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="comment">// method()这个方法存在的意义就是调用Inner这个内部类的show()方法</span></span><br><span class="line"> <span class="keyword">void</span> <span class="title function_">method</span><span class="params">()</span> {</span><br><span class="line"> <span class="comment">// 在method()方法里创建内部类对象,并调用</span></span><br><span class="line"> <span class="type">Inner</span> <span class="variable">in</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">Inner</span>();</span><br><span class="line"> in.show();</span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="comment">// 内部类测试类</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">Demo</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> {</span><br><span class="line"> <span class="comment">// 创建Outer类对象</span></span><br><span class="line"> <span class="type">Outer</span> <span class="variable">o</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">Outer</span>();</span><br><span class="line"> <span class="comment">// 调用 method() 方法就相当于调用了内部类里面的 show() 方法</span></span><br><span class="line"> o.method();</span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line">}</span><br></pre></td></tr></table></figure><h2 id="1-2-局部内部类"><a href="#1-2-局部内部类" class="headerlink" title="1.2 局部内部类"></a>1.2 局部内部类</h2><blockquote><p>局部内部类特点:</p></blockquote><p> 局部内部类是在方法中定义类,所以外界是无法直接使用的,需要在方法内部创建对象并使用。</p><p> 该类可以直接访问外部的成员,也可以访问方法内的局部变量。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">Outer</span> {</span><br><span class="line"> <span class="keyword">private</span> <span class="type">int</span> <span class="variable">num</span> <span class="operator">=</span> <span class="number">10</span>;</span><br><span class="line"></span><br><span class="line"> <span class="keyword">void</span> <span class="title function_">method</span><span class="params">()</span> {</span><br><span class="line"> <span class="type">int</span> <span class="variable">num2</span> <span class="operator">=</span> <span class="number">20</span>;</span><br><span class="line"> <span class="keyword">class</span> <span class="title class_">Inner</span> {</span><br><span class="line"> <span class="keyword">void</span> <span class="title function_">show</span><span class="params">()</span> {</span><br><span class="line"> System.out.println(num);</span><br><span class="line"> System.out.println(num2);</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> <span class="type">Inner</span> <span class="variable">i</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">Inner</span>();</span><br><span class="line"> i.show();</span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">OuterDemo</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> {</span><br><span class="line"> <span class="type">Outer</span> <span class="variable">o</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">Outer</span>();</span><br><span class="line"> o.method();</span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></span><br></pre></td></tr></table></figure><h2 id="1-3-匿名内部类"><a href="#1-3-匿名内部类" class="headerlink" title="1.3 匿名内部类"></a>1.3 匿名内部类</h2><p> 前提:存在一个类或者接口,这里的类可以是具体类也可以是抽象类</p><ul><li>格式</li></ul><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">new</span> 类名或者接口名() {</span><br><span class="line"> 重写方法;</span><br><span class="line">}</span><br></pre></td></tr></table></figure><ul><li>范例</li></ul><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">new</span> <span class="title class_">Inter</span>() {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">show</span><span class="params">()</span> {</span><br><span class="line"></span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><p><strong>匿名内部类本质:是一个继承了该类或者实现了该接口的子类匿名对象</strong></p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">interface</span> <span class="title class_">Inter</span> { <span class="comment">// 这是一个接口,里面有一个show()方法</span></span><br><span class="line"> <span class="keyword">void</span> <span class="title function_">show</span><span class="params">()</span>;</span><br><span class="line">}</span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">Outer</span> {</span><br><span class="line"> <span class="keyword">void</span> <span class="title function_">method</span><span class="params">()</span> {</span><br><span class="line"></span><br><span class="line"> <span class="keyword">new</span> <span class="title class_">Inter</span>() { <span class="comment">// n</span></span><br><span class="line"></span><br><span class="line"> <span class="meta">@Override</span></span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">void</span> <span class="title function_">show</span><span class="params">()</span> {</span><br><span class="line"> System.out.println(<span class="string">"匿名内部类"</span>);</span><br><span class="line"> }</span><br><span class="line"></span><br><span class="line"> }.show();</span><br><span class="line"></span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">OuterDemo</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> {</span><br><span class="line"> <span class="type">Outer</span> <span class="variable">o</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">Outer</span>();</span><br><span class="line"> o.method();</span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></span><br></pre></td></tr></table></figure><h1 id="六、IO"><a href="#六、IO" class="headerlink" title="六、IO"></a>六、IO</h1><h2 id="字符缓冲流复制文件"><a href="#字符缓冲流复制文件" class="headerlink" title="字符缓冲流复制文件"></a>字符缓冲流复制文件</h2><ul><li><p>BufferedReder 字符缓冲输入流</p></li><li><p>BufferedWrite 字符缓冲输出流</p></li></ul><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.itheima.myIo.myCharStream.demo04;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> java.io.*;</span><br><span class="line"></span><br><span class="line"><span class="comment">/*</span></span><br><span class="line"><span class="comment"> 需求:</span></span><br><span class="line"><span class="comment"> 使用字符缓冲流特有功能复制Java文件</span></span><br><span class="line"><span class="comment"> 数据源:D:\IdeaProject\study\src\com\itheima\myIo\myOutputStream\FileOutputStreamDemo02.java</span></span><br><span class="line"><span class="comment"> 目的地:D:\IdeaProject\study\src\com\itheima\myIo\myCharStream\demo04\Copy.java</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">BufferStreamDemo04</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> <span class="keyword">throws</span> IOException {</span><br><span class="line"> <span class="comment">// 字符缓冲输入流</span></span><br><span class="line"> <span class="type">BufferedReader</span> <span class="variable">br</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">BufferedReader</span>(<span class="keyword">new</span> <span class="title class_">FileReader</span>(<span class="string">"D:\\IdeaProject\\study\\src\\com\\itheima\\myIo\\myOutputStream\\FileOutputStreamDemo02.java"</span>));</span><br><span class="line"> <span class="comment">// 字符缓冲输出流</span></span><br><span class="line"> <span class="type">BufferedWriter</span> <span class="variable">bw</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">BufferedWriter</span>(<span class="keyword">new</span> <span class="title class_">FileWriter</span>(<span class="string">"D:\\IdeaProject\\study\\src\\com\\itheima\\myIo\\myCharStream\\demo04\\Copy.java"</span>));</span><br><span class="line"></span><br><span class="line"> String line;</span><br><span class="line"> <span class="keyword">while</span> ((line = br.readLine()) != <span class="literal">null</span>) {</span><br><span class="line"> System.out.println(line);</span><br><span class="line"> bw.write(line);</span><br><span class="line"> bw.newLine();</span><br><span class="line"> bw.flush();</span><br><span class="line"> }</span><br><span class="line"> bw.close();</span><br><span class="line"> br.close();</span><br><span class="line"> }</span><br><span class="line">}</span><br><span class="line"></span><br></pre></td></tr></table></figure><h1 id="十一、网络编程基础"><a href="#十一、网络编程基础" class="headerlink" title="十一、网络编程基础"></a>十一、网络编程基础</h1><h2 id="1-1-网络编程概述"><a href="#1-1-网络编程概述" class="headerlink" title="1.1 网络编程概述"></a>1.1 网络编程概述</h2><p> 计算机网络</p><ul><li>是指将地理位置不同的具有独立功能的多台计算机及其外部设备,通过通信线路连接起来,在网络操作<br> 系统,网络管理软件及网络通信协议的管理和协调下,实现资源共享和信息传递的计算机系统</li></ul><p> 网络编程</p><ul><li>在网络通信协议下,实现网络互连的不同计算机上运行的程序间可以进行数据交换</li></ul><h2 id="1-2-网络编程三要素"><a href="#1-2-网络编程三要素" class="headerlink" title="1.2 网络编程三要素"></a>1.2 网络编程三要素</h2><ol><li><strong>IP地址</strong></li></ol><ul><li>要想让网络中的计算机能够互相通信,必须为每台计算机指定一个标识号,通过这个标识号来指定要接收数<br> 据的计算机和识别发送的计算机,而IP地址就是这个标识号。也就是设备的标识</li></ul><ol><li><strong>端口</strong></li></ol><ul><li>网络的通信,本质上是两个应用程序的通信。每台计算机都有很多的应用程序,那么在网络通信时,如何区<br> 分这些应用程序呢?如果说IP地址可以唯一标识网络中的设备,那么端口号就可以唯一标识设备中的应用程序<br> 了。也就是应用程序的标识</li></ul><ol><li><strong>通信协议</strong></li></ol><ul><li>通过计算机网络可以使多台计算机实现连接,位于同一个网络中的计算机在进行连接和通信时需要遵守一定<br> 的规则,这就好比在道路中行驶的汽车一定要遵守交通规则一样。在计算机网络中,这些连接和通信的规则<br> 被称为网络通信协议,它对数据的传输格式、传输速率、传输步骤等做了统一规定,通信双方必须同时遵守<br> 才能完成数据交换。常见的协议有UDP协议和TCP协议</li></ul><h2 id="1-3-IP地址"><a href="#1-3-IP地址" class="headerlink" title="1.3 IP地址"></a>1.3 IP地址</h2><p>IP地址:是网络中设备的唯一标识</p><p>IP地址分为两大类</p><ul><li>IPv4:是给每个连接在网络上的主机分配一个32bit地址。按照TCP/IP规定,IP地址用二进制来表示,每个IP地址长<br> 32bit,也就是4个字节。例如一个采用二进制形式的IP地址是“110000001010100000000001 01000010”,这么长<br> 的地址,处理起来也太费劲了。为了方便使用,IP地址经常被写成十进制的形式,中间使用符号“.”分隔不同的字节。<br> 于是,上面的IP地址可以表示为“192.168.1.66”。IP地址的这种表示法叫做“点分十进制表示法”,这显然比1和0容<br> 易记忆得多</li><li>由于互联网的蓬勃发展,IP地址的需求量愈来愈大,但是网络地址资源有限,使得IP的分配越发紧张。为了扩大<br> 地址空间,通过IPv6重新定义地址空间,采用128位地址长度,每16个字节一组,分成8组十六进制数,这样就解决了网络地址资源数量不够的问题</li></ul><p>常用命令</p><ul><li>ipconfig:查看本机IP地址</li><li>ping IP地址:检查网络是否连通</li></ul><p>特使IP地址:</p><ul><li>127.0.0.1:回送地址,可以代表本机,一般用来测试</li></ul><h2 id="1-4-InerAddress的使用"><a href="#1-4-InerAddress的使用" class="headerlink" title="1.4 InerAddress的使用"></a>1.4 InerAddress的使用</h2><p>为了方便我们对IP地址的获取和操作, Java提供了一个类InetAddress供我们使用</p><ul><li><p>InetAddress:此类表示Internet协议(IP)地址</p><p> <img src="D:\typoraImages\uTools_1638448531651.png" alt="uTools_1638448531651"></p></li></ul><h2 id="1-5-端口"><a href="#1-5-端口" class="headerlink" title="1.5 端口"></a>1.5 端口</h2><p>端口:设备上应用程序的唯一标识</p><p>端口号:用两个字节表示的整数,它的取值范围是0~65535。其中,0~1023之间的端口号用于一些知名的网<br>络服务和应用,普通的应用程序需要使用1024以上的端口号。如果端口号被另外一个服务或应用所占用,会导<br>致当前程序启动失败</p><h2 id="1-6-协议"><a href="#1-6-协议" class="headerlink" title="1.6 协议"></a>1.6 协议</h2><p>协议:计算机网络中,连接和通信的规则被称为网络通信协议</p><p><span style="color: red"><strong>UDP协议</strong></span></p><ul><li>用户数据报协议(User Datagram Protocol)</li><li>UDP是无连接通信协议,即在数据传输时,数据的发送端和接收端不建立逻辑连接。简单来说,当一台计算机向另外一台计算机发送数据时,发送端不会确认接收端是否存在,就会发出数据,同样接收端在收到数据时,也不会向发送端反馈是否收到数据。</li><li>由于使用UDP协议消耗资源小,通信效率高,所以通常都会用于音频、视频和普通数据的传输</li><li>例如视频会议通常采用UDP协议,因为这种情况即使偶尔丢失一两个数据包,也不会对接收结果产生太大影响。但是在使用UDP协议传送数据时,由于UDP的面向无连接性,不能保证数据的完整性,因此在传输重要数据时不建议使用UDP协议</li></ul><p><span style="color: red"><strong>TCP协议</strong></span></p><ul><li><p>传输控制协议(Transmission Control Protocol)</p></li><li><p>TCP协议是<span style="color:red">面向连接</span>的通信协议,即传输数据之前,在发送端和接收端建立逻辑连接,然后再传输数据,<br> 它提供了两台计算机之间<span style="color:red">可靠无差错</span>的数据传输。在TCP连接中必须要明确客户端与服务器端,由客户端<br> 向服务端发出连接请求,每次连接的创建都需要经过“三次握手。</p></li><li><p>三次握手:TCP协议中,在发送数据的准备阶段客户端与服务端之间的三次交互,以保证连接的可靠</p><ul><li><p>第一次握手,客户端向服务器端发出连接请求,等待服务器确认</p></li><li><p>第二次握手,服务器端向客户端回送一个响应,通知客户端收到了连接请求</p></li><li><p>第三次握手,客户端再次向服务器端发送确认信息,确认连接</p><ul><li>完成三次握手,连接建立后,客户端和服务器就可以开始进行数据传输了。这种面向连接的特性,TCP协议可以保证传输数据的安全,所以应用十分广泛。例如上传文件、下载文件、浏览网页等</li></ul></li></ul></li></ul><h2 id="2-UDP通信程序"><a href="#2-UDP通信程序" class="headerlink" title="2. UDP通信程序"></a>2. UDP通信程序</h2><h5 id="2-1-UDP通信原理"><a href="#2-1-UDP通信原理" class="headerlink" title="2.1 UDP通信原理"></a>2.1 UDP通信原理</h5><p>UDP协议是一种不可靠的网络协议,它在通信的两端各建立一个Socket对象,但是这两个Socket只是发送,接收数据的对象</p><p>因此对于基于UDP协议的通信双方而言,没有所谓的客户端和服务器的概念</p><p>Java提供了DatagramSocket类作为基于UDP协议的Socket</p><h5 id="2-2-UDP发送数据"><a href="#2-2-UDP发送数据" class="headerlink" title="2.2 UDP发送数据"></a>2.2 UDP发送数据</h5><p>发送数据的步骤</p><ol><li>创建发送端的Socket对象(DatagramSocket)</li><li>创建数据,并把数据打包</li><li>调用DatagramSocket对象的方法发送数据</li><li>关闭发送端</li></ol><p>发送数据的步骤<br>① 创建发送端的Socket对象(DatagramSocket)<br> DatagramSocket()<br>② 创建数据,并把数据打包<br> DatagramPacket(byte[] buf, int length, InetAddress address, int port)<br>③ 调用DatagramSocket对象的方法发送数据<br> void send(DatagramPacket p)<br>④ 关闭发送端<br> void close()</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.itheima.MyNet.itheima02;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> java.io.IOException;</span><br><span class="line"><span class="keyword">import</span> java.net.*;</span><br><span class="line"><span class="keyword">import</span> java.nio.charset.StandardCharsets;</span><br><span class="line"></span><br><span class="line"><span class="comment">/*</span></span><br><span class="line"><span class="comment"> 1. 创建发送端的Socket对象(DatagramSocket)</span></span><br><span class="line"><span class="comment"> 2. 创建数据,并把数据打包</span></span><br><span class="line"><span class="comment"> 3. 调用DatagramSocket对象的方法发送数据</span></span><br><span class="line"><span class="comment"> 4. 关闭发送端</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">SendDemo</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> <span class="keyword">throws</span> IOException {</span><br><span class="line"> <span class="comment">// 创建发送端的Socket对象(DatagramSocket)</span></span><br><span class="line"> <span class="comment">// 构造方法:DatagramSocket() 构造数据报套接字并将其绑定到本地主机上的任何可用端口。</span></span><br><span class="line"> <span class="type">DatagramSocket</span> <span class="variable">ds</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">DatagramSocket</span>(<span class="number">3306</span>);</span><br><span class="line"></span><br><span class="line"> <span class="comment">// 创建数据,并把数据打包</span></span><br><span class="line"> <span class="comment">// DatagramPacket(byte[] buf, int length, InetAddress address, int port)</span></span><br><span class="line"> <span class="comment">// 构造一个数据包,发送长度为 length的数据包到指定主机上的指定端口号。</span></span><br><span class="line"> <span class="type">byte</span>[] bytes = <span class="string">"大头大头"</span>.getBytes();</span><br><span class="line"><span class="comment">// int len = bytes.length;</span></span><br><span class="line"><span class="comment">// InetAddress address = InetAddress.getByName("10.102.57.46");</span></span><br><span class="line"><span class="comment">// int port = 12345;</span></span><br><span class="line"> <span class="type">DatagramPacket</span> <span class="variable">dp</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">DatagramPacket</span>(bytes, bytes.length,InetAddress.getByName(<span class="string">"2409:8a30:8a43:2240:5ef:bf78:eccc:4d5"</span>),<span class="number">1219</span>);</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"> <span class="comment">// 调用DatagramSocket对象的方法发送数据</span></span><br><span class="line"> ds.send(dp);</span><br><span class="line"></span><br><span class="line"> <span class="comment">// 关闭发送端</span></span><br><span class="line"> ds.close();</span><br><span class="line"></span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><h5 id="2-3-UDP接受数据"><a href="#2-3-UDP接受数据" class="headerlink" title="2.3 UDP接受数据"></a>2.3 UDP接受数据</h5><p>接收数据的步骤<br>① 创建接收端的Socket对象(DatagramSocket)<br>② 创建一个数据包,用于接收数据<br>③ 调用DatagramSocket对象的方法接收数据<br>④ 解析数据包,并把数据在控制台显示关闭接收端</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.itheima.MyNet.itheima02;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> java.io.IOException;</span><br><span class="line"><span class="keyword">import</span> java.net.DatagramPacket;</span><br><span class="line"><span class="keyword">import</span> java.net.DatagramSocket;</span><br><span class="line"><span class="keyword">import</span> java.net.SocketException;</span><br><span class="line"><span class="keyword">import</span> java.util.Arrays;</span><br><span class="line"></span><br><span class="line"><span class="comment">/*</span></span><br><span class="line"><span class="comment"> 接收数据的步骤</span></span><br><span class="line"><span class="comment"> 1. 创建接收端的Socket对象(DatagramSocket)</span></span><br><span class="line"><span class="comment"> 2. 创建一个数据包,用于接收数据</span></span><br><span class="line"><span class="comment"> 3. 调用DatagramSocket对象的方法接收数据</span></span><br><span class="line"><span class="comment"> 4. 解析数据包,并把数据在控制台显示关闭接收端</span></span><br><span class="line"><span class="comment"> 5. 关闭接收端</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">ReceiveDemo</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> <span class="keyword">throws</span> IOException {</span><br><span class="line"> <span class="keyword">while</span>(<span class="literal">true</span>) {</span><br><span class="line"> <span class="comment">// 创建接收端的Socket对象(DatagramSocket)</span></span><br><span class="line"> <span class="type">DatagramSocket</span> <span class="variable">ds</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">DatagramSocket</span>(<span class="number">1219</span>);</span><br><span class="line"></span><br><span class="line"> <span class="comment">// 创建一个数据包,用于接收数据</span></span><br><span class="line"> <span class="type">byte</span>[] bys = <span class="keyword">new</span> <span class="title class_">byte</span>[<span class="number">1024</span>];</span><br><span class="line"> <span class="type">DatagramPacket</span> <span class="variable">dp</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">DatagramPacket</span>(bys, bys.length);</span><br><span class="line"></span><br><span class="line"> <span class="comment">// 调用DatagramSocket对象的方法接收数据</span></span><br><span class="line"> ds.receive(dp);</span><br><span class="line"></span><br><span class="line"> <span class="comment">// 解析数据包,并把数据在控制台显示关闭接收端</span></span><br><span class="line"> <span class="type">byte</span>[] data = dp.getData();</span><br><span class="line"> <span class="type">int</span> <span class="variable">len</span> <span class="operator">=</span> dp.getLength();</span><br><span class="line"> <span class="type">String</span> <span class="variable">dataString</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">String</span>(data,<span class="number">0</span>,len);</span><br><span class="line"> System.out.println(<span class="string">"数据是:"</span> + dataString);</span><br><span class="line"></span><br><span class="line"> <span class="comment">// 关闭接收端</span></span><br><span class="line"> ds.close();</span><br><span class="line"> }</span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><h4 id="3-TCP通信程序"><a href="#3-TCP通信程序" class="headerlink" title="3. TCP通信程序"></a>3. TCP通信程序</h4><h5 id="3-1-TCP通信原理"><a href="#3-1-TCP通信原理" class="headerlink" title="3.1 TCP通信原理"></a>3.1 TCP通信原理</h5><p>TCP通信协议是一种可靠的网络协议,它在通信的两端各建立一个Socket对象,从而在通信的两端形成网络虚拟链路,一旦建立了虚拟的网络链路,两端的程序就可过虚拟链路进行通信</p><p>Java对基于TCP协议的网络提供了良好的封装,使用Socket对象来表示两端的通信端口,并通过Socket产生IO流来进行网络通信,Java为客户端提供了Socket类,为服务器端提供了ServerSocket类</p><p><img src="D:\typoraImages\uTools_1638448732396.png" alt="uTools_1638448732396"></p><h5 id="3-2-TCP发送数据"><a href="#3-2-TCP发送数据" class="headerlink" title="3.2 TCP发送数据"></a>3.2 TCP发送数据</h5><p>发送数据的步骤<br>① 创建客户端的Socket对象(Socket)</p><p> Socket(String host, int ]port)</p><p>② 获取输出流,写数据</p><p> OutPutStream getOutPutStream()</p><p>③ 释放资源</p><p> void close()</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.itheima.MyNet.itheima04;</span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> java.io.*;</span><br><span class="line"><span class="keyword">import</span> java.net.InetAddress;</span><br><span class="line"><span class="keyword">import</span> java.net.Socket;</span><br><span class="line"></span><br><span class="line"><span class="comment">/*</span></span><br><span class="line"><span class="comment"> TCP发送数据的步骤</span></span><br><span class="line"><span class="comment"> ① 创建客户端的Socket对象(Socket)</span></span><br><span class="line"><span class="comment"> ② 获取输出流,写数据</span></span><br><span class="line"><span class="comment"> ③ 释放资源</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">ClientDemo</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> <span class="keyword">throws</span> IOException {</span><br><span class="line"> <span class="comment">//创建客户端的Socket对象(Socket)</span></span><br><span class="line"> <span class="comment">//Socket(InetAddress address, int port) 创建流套接字并将其连接到指定IP地址的指定端口号。</span></span><br><span class="line"><span class="comment">// Socket s = new Socket(InetAddress.getByName("10.102.57.46"),3306);</span></span><br><span class="line"> <span class="comment">//Socket(String host, int port) 创建流套接字并将其连接到指定主机上的指定端口号。</span></span><br><span class="line"> <span class="type">Socket</span> <span class="variable">s</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">Socket</span>(<span class="string">"10.102.57.46"</span>, <span class="number">3306</span>);</span><br><span class="line"></span><br><span class="line"> <span class="comment">//获取输出流,写数据</span></span><br><span class="line"> <span class="comment">//OutputStream getOutputStream() 返回此套接字的输出流。</span></span><br><span class="line"> <span class="type">OutputStream</span> <span class="variable">os</span> <span class="operator">=</span> s.getOutputStream();</span><br><span class="line"> os.write(<span class="string">"这是tcp协议发送的数据"</span>.getBytes());</span><br><span class="line"></span><br><span class="line"> <span class="comment">//释放资源</span></span><br><span class="line"> s.close();</span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><h5 id="3-3-TCP接收数据"><a href="#3-3-TCP接收数据" class="headerlink" title="3.3 TCP接收数据"></a>3.3 TCP接收数据</h5><p>接收数据的步骤<br>① 创建服务器端的Socket对象(ServerSocket)<br> ServerSocket(int port)<br>②监听客户端连接,返回一个Socket对象<br> Socket accept()<br>③获取输入流,读数据,并把数据显示在控制台<br> InputStream getInputStream()<br>④释放资源<br> void close()</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> com.itheima.MyNet.itheima04;</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> java.io.IOException;</span><br><span class="line"><span class="keyword">import</span> java.io.InputStream;</span><br><span class="line"><span class="keyword">import</span> java.net.ServerSocket;</span><br><span class="line"><span class="keyword">import</span> java.net.Socket;</span><br><span class="line"></span><br><span class="line"><span class="comment">/*</span></span><br><span class="line"><span class="comment"> 接收数据的步骤</span></span><br><span class="line"><span class="comment"> ① 创建服务器端的Socket对象(ServerSocket)</span></span><br><span class="line"><span class="comment"> ② 获取输入流,读数据,并把数据显示在控制台</span></span><br><span class="line"><span class="comment"> ③ 释放资源</span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">class</span> <span class="title class_">ServerDemo</span> {</span><br><span class="line"> <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title function_">main</span><span class="params">(String[] args)</span> <span class="keyword">throws</span> IOException {</span><br><span class="line"> <span class="comment">//创建服务器端的Socket对象(ServerSocket)</span></span><br><span class="line"> <span class="type">ServerSocket</span> <span class="variable">serverSocket</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">ServerSocket</span>(<span class="number">7000</span>);</span><br><span class="line"></span><br><span class="line"> <span class="comment">//Socket accept() 侦听要连接到此套接字并接受它。</span></span><br><span class="line"> <span class="type">Socket</span> <span class="variable">accept</span> <span class="operator">=</span> serverSocket.accept();</span><br><span class="line"></span><br><span class="line"> <span class="comment">//获取输入流,读数据,并把数据显示在控制台</span></span><br><span class="line"> <span class="type">InputStream</span> <span class="variable">inputStream</span> <span class="operator">=</span> accept.getInputStream();</span><br><span class="line"> <span class="type">byte</span>[] bys = <span class="keyword">new</span> <span class="title class_">byte</span>[<span class="number">1024</span>];</span><br><span class="line"> <span class="type">int</span> <span class="variable">len</span> <span class="operator">=</span> inputStream.read(bys);</span><br><span class="line"> <span class="type">String</span> <span class="variable">data</span> <span class="operator">=</span> <span class="keyword">new</span> <span class="title class_">String</span>(bys, <span class="number">0</span>, len);</span><br><span class="line"> System.out.println(<span class="string">"数据是:"</span> + data);</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"> <span class="comment">//释放资源</span></span><br><span class="line"> serverSocket.close();</span><br><span class="line"> }</span><br><span class="line">}</span><br></pre></td></tr></table></figure><h1 id="十二、Lambda表达式"><a href="#十二、Lambda表达式" class="headerlink" title="十二、Lambda表达式"></a>十二、Lambda表达式</h1><h2 id="1-1-函数式编程思想概述"><a href="#1-1-函数式编程思想概述" class="headerlink" title="1.1 函数式编程思想概述"></a>1.1 函数式编程思想概述</h2><p><img src="D:\typoraImages\uTools_1639396954033.png" alt="uTools_1639396954033"></p><p>在数学中,函数就是有输入量、输出量的一套计算方案,也就是“拿数据做操作”<br>面向对象思想强调“必须通过对象的形式来做事情”<br>函数式思想则尽量忽略面向对象的复杂语法“强调做什么,而不是以什么形式去做”<br>而我们要学习的Lambda表达式就是函数式思想的体现</p><h4 id="1-2-体验Lambda表达式"><a href="#1-2-体验Lambda表达式" class="headerlink" title="1.2 体验Lambda表达式"></a>1.2 体验Lambda表达式</h4><p>需求:启动一个线程,在控制台输出—句话:多线程程序启动了</p><p>方式1:</p><ul><li>定义一个类MyRunnable实现Runnable接口,重写run()方法</li><li>创建MyRunnable类的对象</li><li>创建Thread类的对象,把MyRunnable的对象作为构造参数传递</li><li>启动线程</li></ul><h1 id="javaWeb介绍"><a href="#javaWeb介绍" class="headerlink" title="javaWeb介绍"></a>javaWeb介绍</h1><p><strong>什么时javaWeb?</strong></p><ul><li>Web:全球广域网,也称为万维网(www),能够通过浏览器访问的<span style="color:red">网站</span></li><li>JavaWeb:是用Java技术来解决相关web互联网领域的技术栈</li></ul><h1 id="十三、正则表达式"><a href="#十三、正则表达式" class="headerlink" title="十三、正则表达式"></a>十三、正则表达式</h1><p>正则表达式定义了字符串组成的规则</p><p>定义:</p><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">var</span> reg = <span class="regexp">/^\w{6,12}$/</span>; <span class="comment">//不要加引号</span></span><br></pre></td></tr></table></figure><p>方法:</p><ul><li>test(str):判断指定字符串是否符合规则,返回true或false</li></ul><h2 id="语法"><a href="#语法" class="headerlink" title="语法"></a>语法</h2><ul><li>^:开始</li><li>$:结束</li><li>[ ]:代表某个范围内的单个字符,如:[0-9] 单个数字字符</li><li>.:代表任意单个字符,除了换行和行结束符</li><li>\w:代表单词字符:字母、数字、下划线(<em>_</em>),相当于[A-Z a-z 0-9<em>_</em>]</li><li>\d:代表数字字符:相当于[0-9]</li><li>量词:</li><li>+:至少一个</li><li>*:零个或多个</li><li>?:零个或一个</li><li>{x}:x个</li><li>{m,}:至少m个</li><li>{m,n}:至少m个,最多n个<!-- markdownlint-disable MD025 --><h1 id="二十、Web核心"><a href="#二十、Web核心" class="headerlink" title="二十、Web核心"></a>二十、Web核心</h1></li></ul><h2 id="一、javaWeb技术栈"><a href="#一、javaWeb技术栈" class="headerlink" title="一、javaWeb技术栈"></a>一、javaWeb技术栈</h2><ul><li>B/S架构:Browser/Server,浏览器/服务器 架构模式,它的特点是,客户端只需要浏览器,应用程序的逻辑和数<br> 据都存储在服务器端。浏览器只需要请求服务器,获取Web资源,服务器把Web资源发送给浏览器即可<!-- markdownlint-disable MD001 --><h4 id="二、HTTP"><a href="#二、HTTP" class="headerlink" title="二、HTTP"></a>二、HTTP</h4></li></ul><h5 id="1-1-概念"><a href="#1-1-概念" class="headerlink" title="1.1 概念"></a>1.1 概念</h5><ul><li>HyperText Transfer Protocol,超文本传输协议,规定了浏览器和服务器之间数据传输的规则</li></ul><h5 id="1-2-HTTP协议特点"><a href="#1-2-HTTP协议特点" class="headerlink" title="1.2 HTTP协议特点"></a>1.2 HTTP协议特点</h5><ol><li>基于TCP协议:面向连接,安全</li><li>基于请求-响应模型的:一次请求对应一次响应</li><li>HTTP协议是无状态的协议:对于事务处理没有记忆能力。每次请求-响应都是独立的。</li></ol><ul><li>缺点:多次请求间不能共享数据。Java中使用会话技术(Cookie、Session)来解决这个问题</li><li>优点:速度快</li></ul><h5 id="1-3-HTTP-请求数据格式‘"><a href="#1-3-HTTP-请求数据格式‘" class="headerlink" title="1.3 HTTP-请求数据格式‘"></a>1.3 HTTP-请求数据格式‘</h5><!-- markdownlint-disable MD033 --><p>请求数据分为3部分:<br><span style="color:red">1.请求行</span>:请求数据的第一行。其中GET表示请求方式,/表示请求资源路径,HTTP/1.1表示协议版本<br><span style="color:red">2.请求头</span>:第二行开始,格式为key:value形式。<br><span style="color:red">3.请求体</span>:POST请求的最后一部分,存放请求参数</p><p><img src="D:\typoraImages\uTools_1639998349113.png" alt="uTools_1639998349113"></p><p>常见的HTTP 请求头:</p><ul><li><p>Host: 表示请求的主机名</p></li><li><p>User-Agent: 浏览器版本,例如Chrome浏览器的标识类似Mozilla/5.0</p><p> Chrome/79,IE浏览器的标识类似Mozilla/5.0 (Windows NT …) like Gecko;</p></li><li><p>Accept:表示浏览器能接收的资源类型,如text/<em>,image/</em>或者<em>/</em>表示所有;</p></li><li><p>Accept-Language:表示浏览器偏好的语言,服务器可以据此返回不同语言的网页;</p></li><li><p>Accept-Encoding:表示浏览器可以支持的压缩类型,例如gzip, deflate等。</p></li></ul><p><img src="D:\typoraImages\uTools_1639998597810.png" alt="uTools_1639998597810"></p><p>GET请求和 POST请求区别:</p><ol><li>GET请求请求参数在请求行中,没有请求体。<pre><code>POST请求请求参数在请求体中</code></pre></li><li>2.GET请求请求参数大小有限制,<pre><code>POST没有</code></pre></li></ol><h5 id="1-HTTP-响应数据格式"><a href="#1-HTTP-响应数据格式" class="headerlink" title="1. HTTP-响应数据格式"></a>1. HTTP-响应数据格式</h5><!-- markdownlint-disable MD033 --><p>响应数据分为3部分:<br><span style="color:red">1.响应行</span>: 响应数据的第一行。其中HTTP/1.1表示协议版本, 200表示响应状态码,OK表示状态码描述<br><span style="color:red">2.响应头</span>: 第二行开始,格式为key:value形式<br><span style="color:red">3.响应体</span>: 最后一部分。存放响应数据</p><p><img src="D:\typoraImages\uTools_1639998972904.png" alt="uTools_1639998972904"></p><p><img src="D:\typoraImages\uTools_1639999011417.png" alt="uTools_1639999011417"></p><p>常见的HTTP 响应头:<br>Content-Type:表示该响应内容的类型,例如text/html,image/jpeg;<br>Content-Length:表示该响应内容的长度(字节数) ;<br>Content-Encoding:表示该响应压缩算法,例如gzip;<br>Cache-Control:指示客户端应如何缓存,例如max-age=300,表示可以最多缓存300秒</p><ul><li>Web服务器是一个应该程序(软件),对HTTP协议的操作进行封装,使得程序员不必直接对协议进行操作,让Web开<br> 发更加便捷。主要功能是“提供网上信息浏览服务“</li></ul><p><img src="D:\typoraImages\uTools_1639999691337.png" alt="uTools_1639999691337"></p><h4 id="1-5-Tomcat"><a href="#1-5-Tomcat" class="headerlink" title="1.5 Tomcat"></a>1.5 Tomcat</h4><p>概念:</p><ul><li><p>Tomcat是Apache软件基金会一个核心项目,是一个开源免费的轻量级Web服务器,支持Servlet/JSP,少量JavaEE规范。</p></li><li><p>JavaEE:Java Enterprise Edition,Java企业版。指Java企业级开发的技术规范总和。包含13项JDBC、JNDI、EJB、RMI、JSP、Servlet、XML、JMS、Java IDL、JTS、JTA、JavaMail、JAF</p></li><li><p>Tomcat也被称为Web容器、Servlet容器。Servlet需要依赖于Tomcat才能运行</p></li></ul><h4 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h4><ol><li>Web 服务器作用?<ul><li>封装HTTP协议操作,简化开发</li><li>可以将web项目部署到服务器中,对外提供网上浏览服务</li></ul></li><li>Tomcat是一个轻量级的Web服务器,支持Servlet/JSP少量<br>JavaEE规范,也称为Web容器,Servlet容器<br>3.<!-- markdownlint-disable MD025 --><h1 id="二十一、IDEA中创建Maven-Web项目"><a href="#二十一、IDEA中创建Maven-Web项目" class="headerlink" title="二十一、IDEA中创建Maven Web项目"></a>二十一、IDEA中创建Maven Web项目</h1></li></ol><ul><li>Web项目构建</li></ul><p><img src="D:\typoraImages\uTools_1640004314147.png" alt="uTools_1640004314147"></p><p><img src="D:\typoraImages\uTools_1640004353879.png" alt="uTools_1640004353879"></p><ul><li>使用骨架创建</li></ul><p><img src="D:\typoraImages\uTools_1640087139632.png" alt="uTools_1640087139632"></p><ul><li>不使用骨架创建</li></ul><p><img src="C:\Users\30697\AppData\Roaming\Typora\typora-user-images\image-20211221195858886.png" alt="image-20211221195858886"></p><p><img src="C:\Users\30697\AppData\Roaming\Typora\typora-user-images\image-20211221200119441.png" alt="image-20211221200119441"><br><!-- markdownlint-disable MD033 --><br><img src="C:\Users\30697\AppData\Roaming\Typora\typora-user-images\image-20211221200217093.png" alt="image-20211221200217093" style="zoom:75%;" /></p><p><img src="C:\Users\30697\AppData\Roaming\Typora\typora-user-images\image-20211221200352792.png" alt="image-20211221200352792"></p><p><img src="C:\Users\30697\AppData\Roaming\Typora\typora-user-images\image-20211221200539688.png" alt="image-20211221200539688"></p><p><img src="C:\Users\30697\AppData\Roaming\Typora\typora-user-images\image-20211221200608894.png" alt="image-20211221200608894"><br><!-- markdownlint-disable MD025 --></p><h1 id="二十二、IDEA中使用Tomcat"><a href="#二十二、IDEA中使用Tomcat" class="headerlink" title="二十二、IDEA中使用Tomcat"></a>二十二、IDEA中使用Tomcat</h1><ul><li>将本地Tomcat集成到IDEA中,然后进行项目部署</li></ul><p><img src="D:\typoraImages\uTools_1640086097462.png" alt="uTools_1640086097462"></p><ul><li>Tomcat Maven 插件</li></ul>]]></content>
<categories>
<category> 编程 </category>
</categories>
<tags>
<tag> Java基础 </tag>
</tags>
</entry>
<entry>
<title>Mysql学习笔记!</title>
<link href="/posts/1.html"/>
<url>/posts/1.html</url>
<content type="html"><![CDATA[<!-- markdownlint-disable MD025 --><h1 id="MySQL学习笔记"><a href="#MySQL学习笔记" class="headerlink" title="MySQL学习笔记"></a>MySQL学习笔记</h1><h2 id="登录和退出MySQL服务器"><a href="#登录和退出MySQL服务器" class="headerlink" title="登录和退出MySQL服务器"></a>登录和退出MySQL服务器</h2><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta prompt_"># </span><span class="language-bash">登录MySQL</span></span><br><span class="line"><span class="meta prompt_">$ </span><span class="language-bash">mysql -u root -p12345612</span></span><br><span class="line"><span class="meta prompt_"></span></span><br><span class="line"><span class="meta prompt_"># </span><span class="language-bash">退出MySQL数据库服务器</span></span><br><span class="line">exit;</span><br></pre></td></tr></table></figure><h2 id="基本语法"><a href="#基本语法" class="headerlink" title="基本语法"></a>基本语法</h2><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br></pre></td><td class="code"><pre><span class="line">-- 显示所有数据库</span><br><span class="line">show databases;</span><br><span class="line"></span><br><span class="line">-- 创建数据库</span><br><span class="line">CREATE DATABASE test;</span><br><span class="line"></span><br><span class="line">-- 切换数据库</span><br><span class="line">use test;</span><br><span class="line"></span><br><span class="line">-- 显示数据库中的所有表</span><br><span class="line">show tables;</span><br><span class="line"></span><br><span class="line">-- 创建数据表</span><br><span class="line">CREATE TABLE pet (</span><br><span class="line"> name VARCHAR(20),</span><br><span class="line"> owner VARCHAR(20),</span><br><span class="line"> species VARCHAR(20),</span><br><span class="line"> sex CHAR(1),</span><br><span class="line"> birth DATE,</span><br><span class="line"> death DATE</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 查看数据表结构</span><br><span class="line">-- describe pet;</span><br><span class="line">desc pet;</span><br><span class="line"></span><br><span class="line">-- 查询表</span><br><span class="line">SELECT * from pet;</span><br><span class="line"></span><br><span class="line">-- 插入数据</span><br><span class="line">INSERT INTO pet VALUES ('puffball', 'Diane', 'hamster', 'f', '1990-03-30', NULL);</span><br><span class="line"></span><br><span class="line">-- 修改数据</span><br><span class="line">UPDATE pet SET name = 'squirrel' where owner = 'Diane';</span><br><span class="line"></span><br><span class="line">-- 删除数据</span><br><span class="line">DELETE FROM pet where name = 'squirrel';</span><br><span class="line"></span><br><span class="line">-- 删除表</span><br><span class="line">DROP TABLE myorder;</span><br></pre></td></tr></table></figure><h2 id="建表约束"><a href="#建表约束" class="headerlink" title="建表约束"></a>建表约束</h2><h3 id="主键约束"><a href="#主键约束" class="headerlink" title="主键约束"></a>主键约束</h3><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br></pre></td><td class="code"><pre><span class="line">-- 主键约束</span><br><span class="line">-- 使某个字段不重复且不得为空,确保表内所有数据的唯一性。</span><br><span class="line">CREATE TABLE user (</span><br><span class="line"> id INT PRIMARY KEY,</span><br><span class="line"> name VARCHAR(20)</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 联合主键</span><br><span class="line">-- 联合主键中的每个字段都不能为空,并且加起来不能和已设置的联合主键重复。</span><br><span class="line">CREATE TABLE user (</span><br><span class="line"> id INT,</span><br><span class="line"> name VARCHAR(20),</span><br><span class="line"> password VARCHAR(20),</span><br><span class="line"> PRIMARY KEY(id, name)</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 自增约束</span><br><span class="line">-- 自增约束的主键由系统自动递增分配。</span><br><span class="line">CREATE TABLE user (</span><br><span class="line"> id INT PRIMARY KEY AUTO_INCREMENT,</span><br><span class="line"> name VARCHAR(20)</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 添加主键约束</span><br><span class="line">-- 如果忘记设置主键,还可以通过SQL语句设置(两种方式):</span><br><span class="line">ALTER TABLE user ADD PRIMARY KEY(id);</span><br><span class="line">ALTER TABLE user MODIFY id INT PRIMARY KEY;</span><br><span class="line"></span><br><span class="line">-- 删除主键</span><br><span class="line">ALTER TABLE user drop PRIMARY KEY;</span><br></pre></td></tr></table></figure><h3 id="唯一主键"><a href="#唯一主键" class="headerlink" title="唯一主键"></a>唯一主键</h3><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line">-- 建表时创建唯一主键</span><br><span class="line">CREATE TABLE user (</span><br><span class="line"> id INT,</span><br><span class="line"> name VARCHAR(20),</span><br><span class="line"> UNIQUE(name)</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 添加唯一主键</span><br><span class="line">-- 如果建表时没有设置唯一建,还可以通过SQL语句设置(两种方式):</span><br><span class="line">ALTER TABLE user ADD UNIQUE(name);</span><br><span class="line">ALTER TABLE user MODIFY name VARCHAR(20) UNIQUE;</span><br><span class="line"></span><br><span class="line">-- 删除唯一主键</span><br><span class="line">ALTER TABLE user DROP INDEX name;</span><br></pre></td></tr></table></figure><h3 id="非空约束"><a href="#非空约束" class="headerlink" title="非空约束"></a>非空约束</h3><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line">-- 建表时添加非空约束</span><br><span class="line">-- 约束某个字段不能为空</span><br><span class="line">CREATE TABLE user (</span><br><span class="line"> id INT,</span><br><span class="line"> name VARCHAR(20) NOT NULL</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 移除非空约束</span><br><span class="line">ALTER TABLE user MODIFY name VARCHAR(20);</span><br></pre></td></tr></table></figure><h3 id="默认约束"><a href="#默认约束" class="headerlink" title="默认约束"></a>默认约束</h3><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line">-- 建表时添加默认约束</span><br><span class="line">-- 约束某个字段的默认值</span><br><span class="line">CREATE TABLE user2 (</span><br><span class="line"> id INT,</span><br><span class="line"> name VARCHAR(20),</span><br><span class="line"> age INT DEFAULT 10</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 移除非空约束</span><br><span class="line">ALTER TABLE user MODIFY age INT;</span><br></pre></td></tr></table></figure><h3 id="外键约束"><a href="#外键约束" class="headerlink" title="外键约束"></a>外键约束</h3><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br></pre></td><td class="code"><pre><span class="line">-- 班级</span><br><span class="line">CREATE TABLE classes (</span><br><span class="line"> id INT PRIMARY KEY,</span><br><span class="line"> name VARCHAR(20)</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 学生表</span><br><span class="line">CREATE TABLE students (</span><br><span class="line"> id INT PRIMARY KEY,</span><br><span class="line"> name VARCHAR(20),</span><br><span class="line"> -- 这里的 class_id 要和 classes 中的 id 字段相关联</span><br><span class="line"> class_id INT,</span><br><span class="line"> -- 表示 class_id 的值必须来自于 classes 中的 id 字段值</span><br><span class="line"> FOREIGN KEY(class_id) REFERENCES classes(id)</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 1. 主表(父表)classes 中没有的数据值,在副表(子表)students 中,是不可以使用的;</span><br><span class="line">-- 2. 主表中的记录被副表引用时,主表不可以被删除。</span><br></pre></td></tr></table></figure><h2 id="数据库的三大设计范式"><a href="#数据库的三大设计范式" class="headerlink" title="数据库的三大设计范式"></a>数据库的三大设计范式</h2><h3 id="1NF"><a href="#1NF" class="headerlink" title="1NF"></a>1NF</h3><p>只要字段值还可以继续拆分,就不满足第一范式。</p><p>范式设计得越详细,对某些实际操作可能会更好,但并非都有好处,需要对项目的实际情况进行设定。</p><h3 id="2NF"><a href="#2NF" class="headerlink" title="2NF"></a>2NF</h3><p>在满足第一范式的前提下,其他列都必须完全依赖于主键列。如果出现不完全依赖,只可能发生在联合主键的情况下:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line">-- 订单表</span><br><span class="line">CREATE TABLE myorder (</span><br><span class="line"> product_id INT,</span><br><span class="line"> customer_id INT,</span><br><span class="line"> product_name VARCHAR(20),</span><br><span class="line"> customer_name VARCHAR(20),</span><br><span class="line"> PRIMARY KEY (product_id, customer_id)</span><br><span class="line">);</span><br></pre></td></tr></table></figure><p>实际上,在这张订单表中,<code>product_name</code> 只依赖于 <code>product_id</code> ,<code>customer_name</code> 只依赖于 <code>customer_id</code> 。也就是说,<code>product_name</code> 和 <code>customer_id</code> 是没用关系的,<code>customer_name</code> 和 <code>product_id</code> 也是没有关系的。</p><p>这就不满足第二范式:其他列都必须完全依赖于主键列!</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br></pre></td><td class="code"><pre><span class="line">CREATE TABLE myorder (</span><br><span class="line"> order_id INT PRIMARY KEY,</span><br><span class="line"> product_id INT,</span><br><span class="line"> customer_id INT</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">CREATE TABLE product (</span><br><span class="line"> id INT PRIMARY KEY,</span><br><span class="line"> name VARCHAR(20)</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">CREATE TABLE customer (</span><br><span class="line"> id INT PRIMARY KEY,</span><br><span class="line"> name VARCHAR(20)</span><br><span class="line">);</span><br></pre></td></tr></table></figure><p>拆分之后,<code>myorder</code> 表中的 <code>product_id</code> 和 <code>customer_id</code> 完全依赖于 <code>order_id</code> 主键,而 <code>product</code> 和 <code>customer</code> 表中的其他字段又完全依赖于主键。满足了第二范式的设计!</p><h3 id="3NF"><a href="#3NF" class="headerlink" title="3NF"></a>3NF</h3><p>在满足第二范式的前提下,除了主键列之外,其他列之间不能有传递依赖关系。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">CREATE TABLE myorder (</span><br><span class="line"> order_id INT PRIMARY KEY,</span><br><span class="line"> product_id INT,</span><br><span class="line"> customer_id INT,</span><br><span class="line"> customer_phone VARCHAR(15)</span><br><span class="line">);</span><br></pre></td></tr></table></figure><p>表中的 <code>customer_phone</code> 有可能依赖于 <code>order_id</code> 、 <code>customer_id</code> 两列,也就不满足了第三范式的设计:其他列之间不能有传递依赖关系。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line">CREATE TABLE myorder (</span><br><span class="line"> order_id INT PRIMARY KEY,</span><br><span class="line"> product_id INT,</span><br><span class="line"> customer_id INT</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">CREATE TABLE customer (</span><br><span class="line"> id INT PRIMARY KEY,</span><br><span class="line"> name VARCHAR(20),</span><br><span class="line"> phone VARCHAR(15)</span><br><span class="line">);</span><br></pre></td></tr></table></figure><p>修改后就不存在其他列之间的传递依赖关系,其他列都只依赖于主键列,满足了第三范式的设计!</p><h2 id="查询练习"><a href="#查询练习" class="headerlink" title="查询练习"></a>查询练习</h2><h3 id="准备数据"><a href="#准备数据" class="headerlink" title="准备数据"></a>准备数据</h3><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br><span class="line">56</span><br><span class="line">57</span><br><span class="line">58</span><br><span class="line">59</span><br><span class="line">60</span><br><span class="line">61</span><br><span class="line">62</span><br><span class="line">63</span><br><span class="line">64</span><br><span class="line">65</span><br><span class="line">66</span><br><span class="line">67</span><br><span class="line">68</span><br><span class="line">69</span><br><span class="line">70</span><br><span class="line">71</span><br><span class="line">72</span><br><span class="line">73</span><br><span class="line">74</span><br><span class="line">75</span><br><span class="line">76</span><br><span class="line">77</span><br><span class="line">78</span><br><span class="line">79</span><br><span class="line">80</span><br><span class="line">81</span><br><span class="line">82</span><br><span class="line">83</span><br><span class="line">84</span><br><span class="line">85</span><br><span class="line">86</span><br><span class="line">87</span><br></pre></td><td class="code"><pre><span class="line">-- 创建数据库</span><br><span class="line">CREATE DATABASE select_test;</span><br><span class="line">-- 切换数据库</span><br><span class="line">USE select_test;</span><br><span class="line"></span><br><span class="line">-- 创建学生表</span><br><span class="line">CREATE TABLE student (</span><br><span class="line"> no VARCHAR(20) PRIMARY KEY,</span><br><span class="line"> name VARCHAR(20) NOT NULL,</span><br><span class="line"> sex VARCHAR(10) NOT NULL,</span><br><span class="line"> birthday DATE, -- 生日</span><br><span class="line"> class VARCHAR(20) -- 所在班级</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 创建教师表</span><br><span class="line">CREATE TABLE teacher (</span><br><span class="line"> no VARCHAR(20) PRIMARY KEY,</span><br><span class="line"> name VARCHAR(20) NOT NULL,</span><br><span class="line"> sex VARCHAR(10) NOT NULL,</span><br><span class="line"> birthday DATE,</span><br><span class="line"> profession VARCHAR(20) NOT NULL, -- 职称</span><br><span class="line"> department VARCHAR(20) NOT NULL -- 部门</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 创建课程表</span><br><span class="line">CREATE TABLE course (</span><br><span class="line"> no VARCHAR(20) PRIMARY KEY,</span><br><span class="line"> name VARCHAR(20) NOT NULL,</span><br><span class="line"> t_no VARCHAR(20) NOT NULL, -- 教师编号</span><br><span class="line"> -- 表示该 tno 来自于 teacher 表中的 no 字段值</span><br><span class="line"> FOREIGN KEY(t_no) REFERENCES teacher(no)</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 成绩表</span><br><span class="line">CREATE TABLE score (</span><br><span class="line"> s_no VARCHAR(20) NOT NULL, -- 学生编号</span><br><span class="line"> c_no VARCHAR(20) NOT NULL, -- 课程号</span><br><span class="line"> degree DECIMAL, -- 成绩</span><br><span class="line"> -- 表示该 s_no, c_no 分别来自于 student, course 表中的 no 字段值</span><br><span class="line"> FOREIGN KEY(s_no) REFERENCES student(no),</span><br><span class="line"> FOREIGN KEY(c_no) REFERENCES course(no),</span><br><span class="line"> -- 设置 s_no, c_no 为联合主键</span><br><span class="line"> PRIMARY KEY(s_no, c_no)</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">-- 查看所有表</span><br><span class="line">SHOW TABLES;</span><br><span class="line"></span><br><span class="line">-- 添加学生表数据</span><br><span class="line">INSERT INTO student VALUES('101', '曾华', '男', '1977-09-01', '95033');</span><br><span class="line">INSERT INTO student VALUES('102', '匡明', '男', '1975-10-02', '95031');</span><br><span class="line">INSERT INTO student VALUES('103', '王丽', '女', '1976-01-23', '95033');</span><br><span class="line">INSERT INTO student VALUES('104', '李军', '男', '1976-02-20', '95033');</span><br><span class="line">INSERT INTO student VALUES('105', '王芳', '女', '1975-02-10', '95031');</span><br><span class="line">INSERT INTO student VALUES('106', '陆军', '男', '1974-06-03', '95031');</span><br><span class="line">INSERT INTO student VALUES('107', '王尼玛', '男', '1976-02-20', '95033');</span><br><span class="line">INSERT INTO student VALUES('108', '张全蛋', '男', '1975-02-10', '95031');</span><br><span class="line">INSERT INTO student VALUES('109', '赵铁柱', '男', '1974-06-03', '95031');</span><br><span class="line"></span><br><span class="line">-- 添加教师表数据</span><br><span class="line">INSERT INTO teacher VALUES('804', '李诚', '男', '1958-12-02', '副教授', '计算机系');</span><br><span class="line">INSERT INTO teacher VALUES('856', '张旭', '男', '1969-03-12', '讲师', '电子工程系');</span><br><span class="line">INSERT INTO teacher VALUES('825', '王萍', '女', '1972-05-05', '助教', '计算机系');</span><br><span class="line">INSERT INTO teacher VALUES('831', '刘冰', '女', '1977-08-14', '助教', '电子工程系');</span><br><span class="line"></span><br><span class="line">-- 添加课程表数据</span><br><span class="line">INSERT INTO course VALUES('3-105', '计算机导论', '825');</span><br><span class="line">INSERT INTO course VALUES('3-245', '操作系统', '804');</span><br><span class="line">INSERT INTO course VALUES('6-166', '数字电路', '856');</span><br><span class="line">INSERT INTO course VALUES('9-888', '高等数学', '831');</span><br><span class="line"></span><br><span class="line">-- 添加添加成绩表数据</span><br><span class="line">INSERT INTO score VALUES('103', '3-105', '92');</span><br><span class="line">INSERT INTO score VALUES('103', '3-245', '86');</span><br><span class="line">INSERT INTO score VALUES('103', '6-166', '85');</span><br><span class="line">INSERT INTO score VALUES('105', '3-105', '88');</span><br><span class="line">INSERT INTO score VALUES('105', '3-245', '75');</span><br><span class="line">INSERT INTO score VALUES('105', '6-166', '79');</span><br><span class="line">INSERT INTO score VALUES('109', '3-105', '76');</span><br><span class="line">INSERT INTO score VALUES('109', '3-245', '68');</span><br><span class="line">INSERT INTO score VALUES('109', '6-166', '81');</span><br><span class="line"></span><br><span class="line">-- 查看表结构</span><br><span class="line">SELECT * FROM course;</span><br><span class="line">SELECT * FROM score;</span><br><span class="line">SELECT * FROM student;</span><br><span class="line">SELECT * FROM teacher;</span><br></pre></td></tr></table></figure><h3 id="1-到-10"><a href="#1-到-10" class="headerlink" title="1 到 10"></a>1 到 10</h3><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br></pre></td><td class="code"><pre><span class="line">-- 查询 student 表的所有行</span><br><span class="line">SELECT * FROM student;</span><br><span class="line"></span><br><span class="line">-- 查询 student 表中的 name、sex 和 class 字段的所有行</span><br><span class="line">SELECT name, sex, class FROM student;</span><br><span class="line"></span><br><span class="line">-- 查询 teacher 表中不重复的 department 列</span><br><span class="line">-- department: 去重查询</span><br><span class="line">SELECT DISTINCT department FROM teacher;</span><br><span class="line"></span><br><span class="line">-- 查询 score 表中成绩在60-80之间的所有行(区间查询和运算符查询)</span><br><span class="line">-- BETWEEN xx AND xx: 查询区间, AND 表示 "并且"</span><br><span class="line">SELECT * FROM score WHERE degree BETWEEN 60 AND 80;</span><br><span class="line">SELECT * FROM score WHERE degree > 60 AND degree < 80;</span><br><span class="line"></span><br><span class="line">-- 查询 score 表中成绩为 85, 86 或 88 的行</span><br><span class="line">-- IN: 查询规定中的多个值</span><br><span class="line">SELECT * FROM score WHERE degree IN (85, 86, 88);</span><br><span class="line"></span><br><span class="line">-- 查询 student 表中 '95031' 班或性别为 '女' 的所有行</span><br><span class="line">-- or: 表示或者关系</span><br><span class="line">SELECT * FROM student WHERE class = '95031' or sex = '女';</span><br><span class="line"></span><br><span class="line">-- 以 class 降序的方式查询 student 表的所有行</span><br><span class="line">-- DESC: 降序,从高到低</span><br><span class="line">-- ASC(默认): 升序,从低到高</span><br><span class="line">SELECT * FROM student ORDER BY class DESC;</span><br><span class="line">SELECT * FROM student ORDER BY class ASC;</span><br><span class="line"></span><br><span class="line">-- 以 c_no 升序、degree 降序查询 score 表的所有行</span><br><span class="line">SELECT * FROM score ORDER BY c_no ASC, degree DESC;</span><br><span class="line"></span><br><span class="line">-- 查询 "95031" 班的学生人数</span><br><span class="line">-- COUNT: 统计</span><br><span class="line">SELECT COUNT(*) FROM student WHERE class = '95031';</span><br><span class="line"></span><br><span class="line">-- 查询 score 表中的最高分的学生学号和课程编号(子查询或排序查询)。</span><br><span class="line">-- (SELECT MAX(degree) FROM score): 子查询,算出最高分</span><br><span class="line">SELECT s_no, c_no FROM score WHERE degree = (SELECT MAX(degree) FROM score);</span><br><span class="line"></span><br><span class="line">-- 排序查询</span><br><span class="line">-- LIMIT r, n: 表示从第r行开始,查询n条数据</span><br><span class="line">SELECT s_no, c_no, degree FROM score ORDER BY degree DESC LIMIT 0, 1;</span><br></pre></td></tr></table></figure><h3 id="分组计算平均成绩"><a href="#分组计算平均成绩" class="headerlink" title="分组计算平均成绩"></a>分组计算平均成绩</h3><p><strong>查询每门课的平均成绩。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">-- AVG: 平均值</span><br><span class="line">SELECT AVG(degree) FROM score WHERE c_no = '3-105';</span><br><span class="line">SELECT AVG(degree) FROM score WHERE c_no = '3-245';</span><br><span class="line">SELECT AVG(degree) FROM score WHERE c_no = '6-166';</span><br><span class="line"></span><br><span class="line">-- GROUP BY: 分组查询</span><br><span class="line">SELECT c_no, AVG(degree) FROM score GROUP BY c_no;</span><br></pre></td></tr></table></figure><h3 id="分组条件与模糊查询"><a href="#分组条件与模糊查询" class="headerlink" title="分组条件与模糊查询"></a>分组条件与模糊查询</h3><p><strong>查询 <code>score</code> 表中至少有 2 名学生选修,并以 3 开头的课程的平均分数。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br></pre></td><td class="code"><pre><span class="line">SELECT * FROM score;</span><br><span class="line">-- c_no 课程编号</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 103 | 3-105 | 92 |</span><br><span class="line">| 103 | 3-245 | 86 |</span><br><span class="line">| 103 | 6-166 | 85 |</span><br><span class="line">| 105 | 3-105 | 88 |</span><br><span class="line">| 105 | 3-245 | 75 |</span><br><span class="line">| 105 | 6-166 | 79 |</span><br><span class="line">| 109 | 3-105 | 76 |</span><br><span class="line">| 109 | 3-245 | 68 |</span><br><span class="line">| 109 | 6-166 | 81 |</span><br><span class="line">+------+-------+--------+</span><br></pre></td></tr></table></figure><p>分析表发现,至少有 2 名学生选修的课程是 <code>3-105</code> 、<code>3-245</code> 、<code>6-166</code> ,以 3 开头的课程是 <code>3-105</code> 、<code>3-245</code> 。也就是说,我们要查询所有 <code>3-105</code> 和 <code>3-245</code> 的 <code>degree</code> 平均分。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br></pre></td><td class="code"><pre><span class="line">-- 首先把 c_no, AVG(degree) 通过分组查询出来</span><br><span class="line">SELECT c_no, AVG(degree) FROM score GROUP BY c_no</span><br><span class="line">+-------+-------------+</span><br><span class="line">| c_no | AVG(degree) |</span><br><span class="line">+-------+-------------+</span><br><span class="line">| 3-105 | 85.3333 |</span><br><span class="line">| 3-245 | 76.3333 |</span><br><span class="line">| 6-166 | 81.6667 |</span><br><span class="line">+-------+-------------+</span><br><span class="line"></span><br><span class="line">-- 再查询出至少有 2 名学生选修的课程</span><br><span class="line">-- HAVING: 表示持有</span><br><span class="line">HAVING COUNT(c_no) >= 2</span><br><span class="line"></span><br><span class="line">-- 并且是以 3 开头的课程</span><br><span class="line">-- LIKE 表示模糊查询,"%" 是一个通配符,匹配 "3" 后面的任意字符。</span><br><span class="line">AND c_no LIKE '3%';</span><br><span class="line"></span><br><span class="line">-- 把前面的SQL语句拼接起来,</span><br><span class="line">-- 后面加上一个 COUNT(*),表示将每个分组的个数也查询出来。</span><br><span class="line">SELECT c_no, AVG(degree), COUNT(*) FROM score GROUP BY c_no</span><br><span class="line">HAVING COUNT(c_no) >= 2 AND c_no LIKE '3%';</span><br><span class="line">+-------+-------------+----------+</span><br><span class="line">| c_no | AVG(degree) | COUNT(*) |</span><br><span class="line">+-------+-------------+----------+</span><br><span class="line">| 3-105 | 85.3333 | 3 |</span><br><span class="line">| 3-245 | 76.3333 | 3 |</span><br><span class="line">+-------+-------------+----------+</span><br></pre></td></tr></table></figure><h3 id="多表查询-1"><a href="#多表查询-1" class="headerlink" title="多表查询 - 1"></a>多表查询 - 1</h3><p><strong>查询所有学生的 <code>name</code>,以及该学生在 <code>score</code> 表中对应的 <code>c_no</code> 和 <code>degree</code> 。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br></pre></td><td class="code"><pre><span class="line">SELECT no, name FROM student;</span><br><span class="line">+-----+-----------+</span><br><span class="line">| no | name |</span><br><span class="line">+-----+-----------+</span><br><span class="line">| 101 | 曾华 |</span><br><span class="line">| 102 | 匡明 |</span><br><span class="line">| 103 | 王丽 |</span><br><span class="line">| 104 | 李军 |</span><br><span class="line">| 105 | 王芳 |</span><br><span class="line">| 106 | 陆军 |</span><br><span class="line">| 107 | 王尼玛 |</span><br><span class="line">| 108 | 张全蛋 |</span><br><span class="line">| 109 | 赵铁柱 |</span><br><span class="line">+-----+-----------+</span><br><span class="line"></span><br><span class="line">SELECT s_no, c_no, degree FROM score;</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 103 | 3-105 | 92 |</span><br><span class="line">| 103 | 3-245 | 86 |</span><br><span class="line">| 103 | 6-166 | 85 |</span><br><span class="line">| 105 | 3-105 | 88 |</span><br><span class="line">| 105 | 3-245 | 75 |</span><br><span class="line">| 105 | 6-166 | 79 |</span><br><span class="line">| 109 | 3-105 | 76 |</span><br><span class="line">| 109 | 3-245 | 68 |</span><br><span class="line">| 109 | 6-166 | 81 |</span><br><span class="line">+------+-------+--------+</span><br></pre></td></tr></table></figure><p>通过分析可以发现,只要把 <code>score</code> 表中的 <code>s_no</code> 字段值替换成 <code>student</code> 表中对应的 <code>name</code> 字段值就可以了,如何做呢?</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line">-- FROM...: 表示从 student, score 表中查询</span><br><span class="line">-- WHERE 的条件表示为,只有在 student.no 和 score.s_no 相等时才显示出来。</span><br><span class="line">SELECT name, c_no, degree FROM student, score</span><br><span class="line">WHERE student.no = score.s_no;</span><br><span class="line">+-----------+-------+--------+</span><br><span class="line">| name | c_no | degree |</span><br><span class="line">+-----------+-------+--------+</span><br><span class="line">| 王丽 | 3-105 | 92 |</span><br><span class="line">| 王丽 | 3-245 | 86 |</span><br><span class="line">| 王丽 | 6-166 | 85 |</span><br><span class="line">| 王芳 | 3-105 | 88 |</span><br><span class="line">| 王芳 | 3-245 | 75 |</span><br><span class="line">| 王芳 | 6-166 | 79 |</span><br><span class="line">| 赵铁柱 | 3-105 | 76 |</span><br><span class="line">| 赵铁柱 | 3-245 | 68 |</span><br><span class="line">| 赵铁柱 | 6-166 | 81 |</span><br><span class="line">+-----------+-------+--------+</span><br></pre></td></tr></table></figure><h3 id="多表查询-2"><a href="#多表查询-2" class="headerlink" title="多表查询 - 2"></a>多表查询 - 2</h3><p><strong>查询所有学生的 <code>no</code> 、课程名称 ( <code>course</code> 表中的 <code>name</code> ) 和成绩 ( <code>score</code> 表中的 <code>degree</code> ) 列。</strong></p><p>只有 <code>score</code> 关联学生的 <code>no</code> ,因此只要查询 <code>score</code> 表,就能找出所有和学生相关的 <code>no</code> 和 <code>degree</code> :</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line">SELECT s_no, c_no, degree FROM score;</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 103 | 3-105 | 92 |</span><br><span class="line">| 103 | 3-245 | 86 |</span><br><span class="line">| 103 | 6-166 | 85 |</span><br><span class="line">| 105 | 3-105 | 88 |</span><br><span class="line">| 105 | 3-245 | 75 |</span><br><span class="line">| 105 | 6-166 | 79 |</span><br><span class="line">| 109 | 3-105 | 76 |</span><br><span class="line">| 109 | 3-245 | 68 |</span><br><span class="line">| 109 | 6-166 | 81 |</span><br><span class="line">+------+-------+--------+</span><br></pre></td></tr></table></figure><p>然后查询 <code>course</code> 表:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line">+-------+-----------------+</span><br><span class="line">| no | name |</span><br><span class="line">+-------+-----------------+</span><br><span class="line">| 3-105 | 计算机导论 |</span><br><span class="line">| 3-245 | 操作系统 |</span><br><span class="line">| 6-166 | 数字电路 |</span><br><span class="line">| 9-888 | 高等数学 |</span><br><span class="line">+-------+-----------------+</span><br></pre></td></tr></table></figure><p>只要把 <code>score</code> 表中的 <code>c_no</code> 替换成 <code>course</code> 表中对应的 <code>name</code> 字段值就可以了。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line">-- 增加一个查询字段 name,分别从 score、course 这两个表中查询。</span><br><span class="line">-- as 表示取一个该字段的别名。</span><br><span class="line">SELECT s_no, name as c_name, degree FROM score, course</span><br><span class="line">WHERE score.c_no = course.no;</span><br><span class="line">+------+-----------------+--------+</span><br><span class="line">| s_no | c_name | degree |</span><br><span class="line">+------+-----------------+--------+</span><br><span class="line">| 103 | 计算机导论 | 92 |</span><br><span class="line">| 105 | 计算机导论 | 88 |</span><br><span class="line">| 109 | 计算机导论 | 76 |</span><br><span class="line">| 103 | 操作系统 | 86 |</span><br><span class="line">| 105 | 操作系统 | 75 |</span><br><span class="line">| 109 | 操作系统 | 68 |</span><br><span class="line">| 103 | 数字电路 | 85 |</span><br><span class="line">| 105 | 数字电路 | 79 |</span><br><span class="line">| 109 | 数字电路 | 81 |</span><br><span class="line">+------+-----------------+--------+</span><br></pre></td></tr></table></figure><h3 id="三表关联查询"><a href="#三表关联查询" class="headerlink" title="三表关联查询"></a>三表关联查询</h3><p><strong>查询所有学生的 <code>name</code> 、课程名 ( <code>course</code> 表中的 <code>name</code> ) 和 <code>degree</code> 。</strong></p><p>只有 <code>score</code> 表中关联学生的学号和课堂号,我们只要围绕着 <code>score</code> 这张表查询就好了。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line">SELECT * FROM score;</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 103 | 3-105 | 92 |</span><br><span class="line">| 103 | 3-245 | 86 |</span><br><span class="line">| 103 | 6-166 | 85 |</span><br><span class="line">| 105 | 3-105 | 88 |</span><br><span class="line">| 105 | 3-245 | 75 |</span><br><span class="line">| 105 | 6-166 | 79 |</span><br><span class="line">| 109 | 3-105 | 76 |</span><br><span class="line">| 109 | 3-245 | 68 |</span><br><span class="line">| 109 | 6-166 | 81 |</span><br><span class="line">+------+-------+--------+</span><br></pre></td></tr></table></figure><p>只要把 <code>s_no</code> 和 <code>c_no</code> 替换成 <code>student</code> 和 <code>srouse</code> 表中对应的 <code>name</code> 字段值就好了。</p><p>首先把 <code>s_no</code> 替换成 <code>student</code> 表中的 <code>name</code> 字段:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line">SELECT name, c_no, degree FROM student, score WHERE student.no = score.s_no;</span><br><span class="line">+-----------+-------+--------+</span><br><span class="line">| name | c_no | degree |</span><br><span class="line">+-----------+-------+--------+</span><br><span class="line">| 王丽 | 3-105 | 92 |</span><br><span class="line">| 王丽 | 3-245 | 86 |</span><br><span class="line">| 王丽 | 6-166 | 85 |</span><br><span class="line">| 王芳 | 3-105 | 88 |</span><br><span class="line">| 王芳 | 3-245 | 75 |</span><br><span class="line">| 王芳 | 6-166 | 79 |</span><br><span class="line">| 赵铁柱 | 3-105 | 76 |</span><br><span class="line">| 赵铁柱 | 3-245 | 68 |</span><br><span class="line">| 赵铁柱 | 6-166 | 81 |</span><br><span class="line">+-----------+-------+--------+</span><br></pre></td></tr></table></figure><p>再把 <code>c_no</code> 替换成 <code>course</code> 表中的 <code>name</code> 字段:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br></pre></td><td class="code"><pre><span class="line">-- 课程表</span><br><span class="line">SELECT no, name FROM course;</span><br><span class="line">+-------+-----------------+</span><br><span class="line">| no | name |</span><br><span class="line">+-------+-----------------+</span><br><span class="line">| 3-105 | 计算机导论 |</span><br><span class="line">| 3-245 | 操作系统 |</span><br><span class="line">| 6-166 | 数字电路 |</span><br><span class="line">| 9-888 | 高等数学 |</span><br><span class="line">+-------+-----------------+</span><br><span class="line"></span><br><span class="line">-- 由于字段名存在重复,使用 "表名.字段名 as 别名" 代替。</span><br><span class="line">SELECT student.name as s_name, course.name as c_name, degree</span><br><span class="line">FROM student, score, course</span><br><span class="line">WHERE student.NO = score.s_no</span><br><span class="line">AND score.c_no = course.no;</span><br></pre></td></tr></table></figure><h3 id="子查询加分组求平均分"><a href="#子查询加分组求平均分" class="headerlink" title="子查询加分组求平均分"></a>子查询加分组求平均分</h3><p><strong>查询 <code>95031</code> 班学生每门课程的平均成绩。</strong></p><p>在 <code>score</code> 表中根据 <code>student</code> 表的学生编号筛选出学生的课堂号和成绩:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line">-- IN (..): 将筛选出的学生号当做 s_no 的条件查询</span><br><span class="line">SELECT s_no, c_no, degree FROM score</span><br><span class="line">WHERE s_no IN (SELECT no FROM student WHERE class = '95031');</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 105 | 3-105 | 88 |</span><br><span class="line">| 105 | 3-245 | 75 |</span><br><span class="line">| 105 | 6-166 | 79 |</span><br><span class="line">| 109 | 3-105 | 76 |</span><br><span class="line">| 109 | 3-245 | 68 |</span><br><span class="line">| 109 | 6-166 | 81 |</span><br><span class="line">+------+-------+--------+</span><br></pre></td></tr></table></figure><p>这时只要将 <code>c_no</code> 分组一下就能得出 <code>95031</code> 班学生每门课的平均成绩:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line">SELECT c_no, AVG(degree) FROM score</span><br><span class="line">WHERE s_no IN (SELECT no FROM student WHERE class = '95031')</span><br><span class="line">GROUP BY c_no;</span><br><span class="line">+-------+-------------+</span><br><span class="line">| c_no | AVG(degree) |</span><br><span class="line">+-------+-------------+</span><br><span class="line">| 3-105 | 82.0000 |</span><br><span class="line">| 3-245 | 71.5000 |</span><br><span class="line">| 6-166 | 80.0000 |</span><br><span class="line">+-------+-------------+</span><br></pre></td></tr></table></figure><h3 id="子查询-1"><a href="#子查询-1" class="headerlink" title="子查询 - 1"></a>子查询 - 1</h3><p><strong>查询在 <code>3-105</code> 课程中,所有成绩高于 <code>109</code> 号同学的记录。</strong></p><p>首先筛选出课堂号为 <code>3-105</code> ,在找出所有成绩高于 <code>109</code> 号同学的的行。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">SELECT * FROM score</span><br><span class="line">WHERE c_no = '3-105'</span><br><span class="line">AND degree > (SELECT degree FROM score WHERE s_no = '109' AND c_no = '3-105');</span><br></pre></td></tr></table></figure><h3 id="子查询-2"><a href="#子查询-2" class="headerlink" title="子查询 - 2"></a>子查询 - 2</h3><p><strong>查询所有成绩高于 <code>109</code> 号同学的 <code>3-105</code> 课程成绩记录。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">-- 不限制课程号,只要成绩大于109号同学的3-105课程成绩就可以。</span><br><span class="line">SELECT * FROM score</span><br><span class="line">WHERE degree > (SELECT degree FROM score WHERE s_no = '109' AND c_no = '3-105');</span><br></pre></td></tr></table></figure><h3 id="YEAR-函数与带-IN-关键字查询"><a href="#YEAR-函数与带-IN-关键字查询" class="headerlink" title="YEAR 函数与带 IN 关键字查询"></a>YEAR 函数与带 IN 关键字查询</h3><p><strong>查询所有和 <code>101</code> 、<code>108</code> 号学生同年出生的 <code>no</code> 、<code>name</code> 、<code>birthday</code> 列。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">-- YEAR(..): 取出日期中的年份</span><br><span class="line">SELECT no, name, birthday FROM student</span><br><span class="line">WHERE YEAR(birthday) IN (SELECT YEAR(birthday) FROM student WHERE no IN (101, 108));</span><br></pre></td></tr></table></figure><h3 id="多层嵌套子查询"><a href="#多层嵌套子查询" class="headerlink" title="多层嵌套子查询"></a>多层嵌套子查询</h3><p><strong>查询 <code>'张旭'</code> 教师任课的学生成绩表。</strong></p><p>首先找到教师编号:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">SELECT NO FROM teacher WHERE NAME = '张旭'</span><br></pre></td></tr></table></figure><p>通过 <code>sourse</code> 表找到该教师课程号:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">SELECT NO FROM course WHERE t_no = ( SELECT NO FROM teacher WHERE NAME = '张旭' );</span><br></pre></td></tr></table></figure><p>通过筛选出的课程号查询成绩表:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">SELECT * FROM score WHERE c_no = (</span><br><span class="line"> SELECT no FROM course WHERE t_no = (</span><br><span class="line"> SELECT no FROM teacher WHERE NAME = '张旭'</span><br><span class="line"> )</span><br><span class="line">);</span><br></pre></td></tr></table></figure><h3 id="多表查询"><a href="#多表查询" class="headerlink" title="多表查询"></a>多表查询</h3><p><strong>查询某选修课程多于5个同学的教师姓名。</strong></p><p>首先在 <code>teacher</code> 表中,根据 <code>no</code> 字段来判断该教师的同一门课程是否有至少5名学员选修:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line">-- 查询 teacher 表</span><br><span class="line">SELECT no, name FROM teacher;</span><br><span class="line">+-----+--------+</span><br><span class="line">| no | name |</span><br><span class="line">+-----+--------+</span><br><span class="line">| 804 | 李诚 |</span><br><span class="line">| 825 | 王萍 |</span><br><span class="line">| 831 | 刘冰 |</span><br><span class="line">| 856 | 张旭 |</span><br><span class="line">+-----+--------+</span><br><span class="line"></span><br><span class="line">SELECT name FROM teacher WHERE no IN (</span><br><span class="line"> -- 在这里找到对应的条件</span><br><span class="line">);</span><br></pre></td></tr></table></figure><p>查看和教师编号有有关的表的信息:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line">SELECT * FROM course;</span><br><span class="line">-- t_no: 教师编号</span><br><span class="line">+-------+-----------------+------+</span><br><span class="line">| no | name | t_no |</span><br><span class="line">+-------+-----------------+------+</span><br><span class="line">| 3-105 | 计算机导论 | 825 |</span><br><span class="line">| 3-245 | 操作系统 | 804 |</span><br><span class="line">| 6-166 | 数字电路 | 856 |</span><br><span class="line">| 9-888 | 高等数学 | 831 |</span><br><span class="line">+-------+-----------------+------+</span><br></pre></td></tr></table></figure><p>我们已经找到和教师编号有关的字段就在 <code>course</code> 表中,但是还无法知道哪门课程至少有5名学生选修,所以还需要根据 <code>score</code> 表来查询:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br></pre></td><td class="code"><pre><span class="line">-- 在此之前向 score 插入一些数据,以便丰富查询条件。</span><br><span class="line">INSERT INTO score VALUES ('101', '3-105', '90');</span><br><span class="line">INSERT INTO score VALUES ('102', '3-105', '91');</span><br><span class="line">INSERT INTO score VALUES ('104', '3-105', '89');</span><br><span class="line"></span><br><span class="line">-- 查询 score 表</span><br><span class="line">SELECT * FROM score;</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 101 | 3-105 | 90 |</span><br><span class="line">| 102 | 3-105 | 91 |</span><br><span class="line">| 103 | 3-105 | 92 |</span><br><span class="line">| 103 | 3-245 | 86 |</span><br><span class="line">| 103 | 6-166 | 85 |</span><br><span class="line">| 104 | 3-105 | 89 |</span><br><span class="line">| 105 | 3-105 | 88 |</span><br><span class="line">| 105 | 3-245 | 75 |</span><br><span class="line">| 105 | 6-166 | 79 |</span><br><span class="line">| 109 | 3-105 | 76 |</span><br><span class="line">| 109 | 3-245 | 68 |</span><br><span class="line">| 109 | 6-166 | 81 |</span><br><span class="line">+------+-------+--------+</span><br><span class="line"></span><br><span class="line">-- 在 score 表中将 c_no 作为分组,并且限制 c_no 持有至少 5 条数据。</span><br><span class="line">SELECT c_no FROM score GROUP BY c_no HAVING COUNT(*) > 5;</span><br><span class="line">+-------+</span><br><span class="line">| c_no |</span><br><span class="line">+-------+</span><br><span class="line">| 3-105 |</span><br><span class="line">+-------+</span><br></pre></td></tr></table></figure><p>根据筛选出来的课程号,找出在某课程中,拥有至少5名学员的教师编号:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line">SELECT t_no FROM course WHERE no IN (</span><br><span class="line"> SELECT c_no FROM score GROUP BY c_no HAVING COUNT(*) > 5</span><br><span class="line">);</span><br><span class="line">+------+</span><br><span class="line">| t_no |</span><br><span class="line">+------+</span><br><span class="line">| 825 |</span><br><span class="line">+------+</span><br></pre></td></tr></table></figure><p>在 <code>teacher</code> 表中,根据筛选出来的教师编号找到教师姓名:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">SELECT name FROM teacher WHERE no IN (</span><br><span class="line"> -- 最终条件</span><br><span class="line"> SELECT t_no FROM course WHERE no IN (</span><br><span class="line"> SELECT c_no FROM score GROUP BY c_no HAVING COUNT(*) > 5</span><br><span class="line"> )</span><br><span class="line">);</span><br></pre></td></tr></table></figure><h3 id="子查询-3"><a href="#子查询-3" class="headerlink" title="子查询 - 3"></a>子查询 - 3</h3><p><strong>查询 “计算机系” 课程的成绩表。</strong></p><p>思路是,先找出 <code>course</code> 表中所有 <code>计算机系</code> 课程的编号,然后根据这个编号查询 <code>score</code> 表。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br></pre></td><td class="code"><pre><span class="line">-- 通过 teacher 表查询所有 `计算机系` 的教师编号</span><br><span class="line">SELECT no, name, department FROM teacher WHERE department = '计算机系'</span><br><span class="line">+-----+--------+--------------+</span><br><span class="line">| no | name | department |</span><br><span class="line">+-----+--------+--------------+</span><br><span class="line">| 804 | 李诚 | 计算机系 |</span><br><span class="line">| 825 | 王萍 | 计算机系 |</span><br><span class="line">+-----+--------+--------------+</span><br><span class="line"></span><br><span class="line">-- 通过 course 表查询该教师的课程编号</span><br><span class="line">SELECT no FROM course WHERE t_no IN (</span><br><span class="line"> SELECT no FROM teacher WHERE department = '计算机系'</span><br><span class="line">);</span><br><span class="line">+-------+</span><br><span class="line">| no |</span><br><span class="line">+-------+</span><br><span class="line">| 3-245 |</span><br><span class="line">| 3-105 |</span><br><span class="line">+-------+</span><br><span class="line"></span><br><span class="line">-- 根据筛选出来的课程号查询成绩表</span><br><span class="line">SELECT * FROM score WHERE c_no IN (</span><br><span class="line"> SELECT no FROM course WHERE t_no IN (</span><br><span class="line"> SELECT no FROM teacher WHERE department = '计算机系'</span><br><span class="line"> )</span><br><span class="line">);</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 103 | 3-245 | 86 |</span><br><span class="line">| 105 | 3-245 | 75 |</span><br><span class="line">| 109 | 3-245 | 68 |</span><br><span class="line">| 101 | 3-105 | 90 |</span><br><span class="line">| 102 | 3-105 | 91 |</span><br><span class="line">| 103 | 3-105 | 92 |</span><br><span class="line">| 104 | 3-105 | 89 |</span><br><span class="line">| 105 | 3-105 | 88 |</span><br><span class="line">| 109 | 3-105 | 76 |</span><br><span class="line">+------+-------+--------+</span><br></pre></td></tr></table></figure><h3 id="UNION-和-NOTIN-的使用"><a href="#UNION-和-NOTIN-的使用" class="headerlink" title="UNION 和 NOTIN 的使用"></a>UNION 和 NOTIN 的使用</h3><p><strong>查询 <code>计算机系</code> 与 <code>电子工程系</code> 中的不同职称的教师。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line">-- NOT: 代表逻辑非</span><br><span class="line">SELECT * FROM teacher WHERE department = '计算机系' AND profession NOT IN (</span><br><span class="line"> SELECT profession FROM teacher WHERE department = '电子工程系'</span><br><span class="line">)</span><br><span class="line">-- 合并两个集</span><br><span class="line">UNION</span><br><span class="line">SELECT * FROM teacher WHERE department = '电子工程系' AND profession NOT IN (</span><br><span class="line"> SELECT profession FROM teacher WHERE department = '计算机系'</span><br><span class="line">);</span><br></pre></td></tr></table></figure><h3 id="ANY-表示至少一个-DESC-降序"><a href="#ANY-表示至少一个-DESC-降序" class="headerlink" title="ANY 表示至少一个 - DESC ( 降序 )"></a>ANY 表示至少一个 - DESC ( 降序 )</h3><!-- markdownlint-disable MD033 --><p><strong>查询课程 <code>3-105</code> 且成绩 <u>至少</u> 高于 <code>3-245</code> 的 <code>score</code> 表。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br></pre></td><td class="code"><pre><span class="line">SELECT * FROM score WHERE c_no = '3-105';</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 101 | 3-105 | 90 |</span><br><span class="line">| 102 | 3-105 | 91 |</span><br><span class="line">| 103 | 3-105 | 92 |</span><br><span class="line">| 104 | 3-105 | 89 |</span><br><span class="line">| 105 | 3-105 | 88 |</span><br><span class="line">| 109 | 3-105 | 76 |</span><br><span class="line">+------+-------+--------+</span><br><span class="line"></span><br><span class="line">SELECT * FROM score WHERE c_no = '3-245';</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 103 | 3-245 | 86 |</span><br><span class="line">| 105 | 3-245 | 75 |</span><br><span class="line">| 109 | 3-245 | 68 |</span><br><span class="line">+------+-------+--------+</span><br><span class="line"></span><br><span class="line">-- ANY: 符合SQL语句中的任意条件。</span><br><span class="line">-- 也就是说,在 3-105 成绩中,只要有一个大于从 3-245 筛选出来的任意行就符合条件,</span><br><span class="line">-- 最后根据降序查询结果。</span><br><span class="line">SELECT * FROM score WHERE c_no = '3-105' AND degree > ANY(</span><br><span class="line"> SELECT degree FROM score WHERE c_no = '3-245'</span><br><span class="line">) ORDER BY degree DESC;</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 103 | 3-105 | 92 |</span><br><span class="line">| 102 | 3-105 | 91 |</span><br><span class="line">| 101 | 3-105 | 90 |</span><br><span class="line">| 104 | 3-105 | 89 |</span><br><span class="line">| 105 | 3-105 | 88 |</span><br><span class="line">| 109 | 3-105 | 76 |</span><br><span class="line">+------+-------+--------+</span><br></pre></td></tr></table></figure><h3 id="表示所有的-ALL"><a href="#表示所有的-ALL" class="headerlink" title="表示所有的 ALL"></a>表示所有的 ALL</h3><p><strong>查询课程 <code>3-105</code> 且成绩高于 <code>3-245</code> 的 <code>score</code> 表。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br></pre></td><td class="code"><pre><span class="line">-- 只需对上一道题稍作修改。</span><br><span class="line">-- ALL: 符合SQL语句中的所有条件。</span><br><span class="line">-- 也就是说,在 3-105 每一行成绩中,都要大于从 3-245 筛选出来全部行才算符合条件。</span><br><span class="line">SELECT * FROM score WHERE c_no = '3-105' AND degree > ALL(</span><br><span class="line"> SELECT degree FROM score WHERE c_no = '3-245'</span><br><span class="line">);</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 101 | 3-105 | 90 |</span><br><span class="line">| 102 | 3-105 | 91 |</span><br><span class="line">| 103 | 3-105 | 92 |</span><br><span class="line">| 104 | 3-105 | 89 |</span><br><span class="line">| 105 | 3-105 | 88 |</span><br><span class="line">+------+-------+--------+</span><br></pre></td></tr></table></figure><h3 id="复制表的数据作为条件查询"><a href="#复制表的数据作为条件查询" class="headerlink" title="复制表的数据作为条件查询"></a>复制表的数据作为条件查询</h3><p><strong>查询某课程成绩比该课程平均成绩低的 <code>score</code> 表。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br></pre></td><td class="code"><pre><span class="line">-- 查询平均分</span><br><span class="line">SELECT c_no, AVG(degree) FROM score GROUP BY c_no;</span><br><span class="line">+-------+-------------+</span><br><span class="line">| c_no | AVG(degree) |</span><br><span class="line">+-------+-------------+</span><br><span class="line">| 3-105 | 87.6667 |</span><br><span class="line">| 3-245 | 76.3333 |</span><br><span class="line">| 6-166 | 81.6667 |</span><br><span class="line">+-------+-------------+</span><br><span class="line"></span><br><span class="line">-- 查询 score 表</span><br><span class="line">SELECT degree FROM score;</span><br><span class="line">+--------+</span><br><span class="line">| degree |</span><br><span class="line">+--------+</span><br><span class="line">| 90 |</span><br><span class="line">| 91 |</span><br><span class="line">| 92 |</span><br><span class="line">| 86 |</span><br><span class="line">| 85 |</span><br><span class="line">| 89 |</span><br><span class="line">| 88 |</span><br><span class="line">| 75 |</span><br><span class="line">| 79 |</span><br><span class="line">| 76 |</span><br><span class="line">| 68 |</span><br><span class="line">| 81 |</span><br><span class="line">+--------+</span><br><span class="line"></span><br><span class="line">-- 将表 b 作用于表 a 中查询数据</span><br><span class="line">-- score a (b): 将表声明为 a (b),</span><br><span class="line">-- 如此就能用 a.c_no = b.c_no 作为条件执行查询了。</span><br><span class="line">SELECT * FROM score a WHERE degree < (</span><br><span class="line"> (SELECT AVG(degree) FROM score b WHERE a.c_no = b.c_no)</span><br><span class="line">);</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 105 | 3-245 | 75 |</span><br><span class="line">| 105 | 6-166 | 79 |</span><br><span class="line">| 109 | 3-105 | 76 |</span><br><span class="line">| 109 | 3-245 | 68 |</span><br><span class="line">| 109 | 6-166 | 81 |</span><br><span class="line">+------+-------+--------+</span><br></pre></td></tr></table></figure><h3 id="子查询-4"><a href="#子查询-4" class="headerlink" title="子查询 - 4"></a>子查询 - 4</h3><p><strong>查询所有任课 ( 在 <code>course</code> 表里有课程 ) 教师的 <code>name</code> 和 <code>department</code></strong> 。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line">SELECT name, department FROM teacher WHERE no IN (SELECT t_no FROM course);</span><br><span class="line">+--------+-----------------+</span><br><span class="line">| name | department |</span><br><span class="line">+--------+-----------------+</span><br><span class="line">| 李诚 | 计算机系 |</span><br><span class="line">| 王萍 | 计算机系 |</span><br><span class="line">| 刘冰 | 电子工程系 |</span><br><span class="line">| 张旭 | 电子工程系 |</span><br><span class="line">+--------+-----------------+</span><br></pre></td></tr></table></figure><h3 id="条件加组筛选"><a href="#条件加组筛选" class="headerlink" title="条件加组筛选"></a>条件加组筛选</h3><p><strong>查询 <code>student</code> 表中至少有 2 名男生的 <code>class</code> 。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br></pre></td><td class="code"><pre><span class="line">-- 查看学生表信息</span><br><span class="line">SELECT * FROM student;</span><br><span class="line">+-----+-----------+-----+------------+-------+</span><br><span class="line">| no | name | sex | birthday | class |</span><br><span class="line">+-----+-----------+-----+------------+-------+</span><br><span class="line">| 101 | 曾华 | 男 | 1977-09-01 | 95033 |</span><br><span class="line">| 102 | 匡明 | 男 | 1975-10-02 | 95031 |</span><br><span class="line">| 103 | 王丽 | 女 | 1976-01-23 | 95033 |</span><br><span class="line">| 104 | 李军 | 男 | 1976-02-20 | 95033 |</span><br><span class="line">| 105 | 王芳 | 女 | 1975-02-10 | 95031 |</span><br><span class="line">| 106 | 陆军 | 男 | 1974-06-03 | 95031 |</span><br><span class="line">| 107 | 王尼玛 | 男 | 1976-02-20 | 95033 |</span><br><span class="line">| 108 | 张全蛋 | 男 | 1975-02-10 | 95031 |</span><br><span class="line">| 109 | 赵铁柱 | 男 | 1974-06-03 | 95031 |</span><br><span class="line">| 110 | 张飞 | 男 | 1974-06-03 | 95038 |</span><br><span class="line">+-----+-----------+-----+------------+-------+</span><br><span class="line"></span><br><span class="line">-- 只查询性别为男,然后按 class 分组,并限制 class 行大于 1。</span><br><span class="line">SELECT class FROM student WHERE sex = '男' GROUP BY class HAVING COUNT(*) > 1;</span><br><span class="line">+-------+</span><br><span class="line">| class |</span><br><span class="line">+-------+</span><br><span class="line">| 95033 |</span><br><span class="line">| 95031 |</span><br><span class="line">+-------+</span><br></pre></td></tr></table></figure><h3 id="NOTLIKE-模糊查询取反"><a href="#NOTLIKE-模糊查询取反" class="headerlink" title="NOTLIKE 模糊查询取反"></a>NOTLIKE 模糊查询取反</h3><p><strong>查询 <code>student</code> 表中不姓 “王” 的同学记录。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line">-- NOT: 取反</span><br><span class="line">-- LIKE: 模糊查询</span><br><span class="line">mysql> SELECT * FROM student WHERE name NOT LIKE '王%';</span><br><span class="line">+-----+-----------+-----+------------+-------+</span><br><span class="line">| no | name | sex | birthday | class |</span><br><span class="line">+-----+-----------+-----+------------+-------+</span><br><span class="line">| 101 | 曾华 | 男 | 1977-09-01 | 95033 |</span><br><span class="line">| 102 | 匡明 | 男 | 1975-10-02 | 95031 |</span><br><span class="line">| 104 | 李军 | 男 | 1976-02-20 | 95033 |</span><br><span class="line">| 106 | 陆军 | 男 | 1974-06-03 | 95031 |</span><br><span class="line">| 108 | 张全蛋 | 男 | 1975-02-10 | 95031 |</span><br><span class="line">| 109 | 赵铁柱 | 男 | 1974-06-03 | 95031 |</span><br><span class="line">| 110 | 张飞 | 男 | 1974-06-03 | 95038 |</span><br><span class="line">+-----+-----------+-----+------------+-------+</span><br></pre></td></tr></table></figure><h3 id="YEAR-与-NOW-函数"><a href="#YEAR-与-NOW-函数" class="headerlink" title="YEAR 与 NOW 函数"></a>YEAR 与 NOW 函数</h3><p><strong>查询 <code>student</code> 表中每个学生的姓名和年龄。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br></pre></td><td class="code"><pre><span class="line">-- 使用函数 YEAR(NOW()) 计算出当前年份,减去出生年份后得出年龄。</span><br><span class="line">SELECT name, YEAR(NOW()) - YEAR(birthday) as age FROM student;</span><br><span class="line">+-----------+------+</span><br><span class="line">| name | age |</span><br><span class="line">+-----------+------+</span><br><span class="line">| 曾华 | 42 |</span><br><span class="line">| 匡明 | 44 |</span><br><span class="line">| 王丽 | 43 |</span><br><span class="line">| 李军 | 43 |</span><br><span class="line">| 王芳 | 44 |</span><br><span class="line">| 陆军 | 45 |</span><br><span class="line">| 王尼玛 | 43 |</span><br><span class="line">| 张全蛋 | 44 |</span><br><span class="line">| 赵铁柱 | 45 |</span><br><span class="line">| 张飞 | 45 |</span><br><span class="line">+-----------+------+</span><br></pre></td></tr></table></figure><h3 id="MAX-与-MIN-函数"><a href="#MAX-与-MIN-函数" class="headerlink" title="MAX 与 MIN 函数"></a>MAX 与 MIN 函数</h3><p><strong>查询 <code>student</code> 表中最大和最小的 <code>birthday</code> 值。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">SELECT MAX(birthday), MIN(birthday) FROM student;</span><br><span class="line">+---------------+---------------+</span><br><span class="line">| MAX(birthday) | MIN(birthday) |</span><br><span class="line">+---------------+---------------+</span><br><span class="line">| 1977-09-01 | 1974-06-03 |</span><br><span class="line">+---------------+---------------+</span><br></pre></td></tr></table></figure><h3 id="多段排序"><a href="#多段排序" class="headerlink" title="多段排序"></a>多段排序</h3><p><strong>以 <code>class</code> 和 <code>birthday</code> 从大到小的顺序查询 <code>student</code> 表。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br></pre></td><td class="code"><pre><span class="line">SELECT * FROM student ORDER BY class DESC, birthday;</span><br><span class="line">+-----+-----------+-----+------------+-------+</span><br><span class="line">| no | name | sex | birthday | class |</span><br><span class="line">+-----+-----------+-----+------------+-------+</span><br><span class="line">| 110 | 张飞 | 男 | 1974-06-03 | 95038 |</span><br><span class="line">| 103 | 王丽 | 女 | 1976-01-23 | 95033 |</span><br><span class="line">| 104 | 李军 | 男 | 1976-02-20 | 95033 |</span><br><span class="line">| 107 | 王尼玛 | 男 | 1976-02-20 | 95033 |</span><br><span class="line">| 101 | 曾华 | 男 | 1977-09-01 | 95033 |</span><br><span class="line">| 106 | 陆军 | 男 | 1974-06-03 | 95031 |</span><br><span class="line">| 109 | 赵铁柱 | 男 | 1974-06-03 | 95031 |</span><br><span class="line">| 105 | 王芳 | 女 | 1975-02-10 | 95031 |</span><br><span class="line">| 108 | 张全蛋 | 男 | 1975-02-10 | 95031 |</span><br><span class="line">| 102 | 匡明 | 男 | 1975-10-02 | 95031 |</span><br><span class="line">+-----+-----------+-----+------------+-------+</span><br></pre></td></tr></table></figure><h3 id="子查询-5"><a href="#子查询-5" class="headerlink" title="子查询 - 5"></a>子查询 - 5</h3><p><strong>查询 “男” 教师及其所上的课程。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">SELECT * FROM course WHERE t_no in (SELECT no FROM teacher WHERE sex = '男');</span><br><span class="line">+-------+--------------+------+</span><br><span class="line">| no | name | t_no |</span><br><span class="line">+-------+--------------+------+</span><br><span class="line">| 3-245 | 操作系统 | 804 |</span><br><span class="line">| 6-166 | 数字电路 | 856 |</span><br><span class="line">+-------+--------------+------+</span><br></pre></td></tr></table></figure><h3 id="MAX-函数与子查询"><a href="#MAX-函数与子查询" class="headerlink" title="MAX 函数与子查询"></a>MAX 函数与子查询</h3><p><strong>查询最高分同学的 <code>score</code> 表。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line">-- 找出最高成绩(该查询只能有一个结果)</span><br><span class="line">SELECT MAX(degree) FROM score;</span><br><span class="line"></span><br><span class="line">-- 根据上面的条件筛选出所有最高成绩表,</span><br><span class="line">-- 该查询可能有多个结果,假设 degree 值多次符合条件。</span><br><span class="line">SELECT * FROM score WHERE degree = (SELECT MAX(degree) FROM score);</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 103 | 3-105 | 92 |</span><br><span class="line">+------+-------+--------+</span><br></pre></td></tr></table></figure><h3 id="子查询-6"><a href="#子查询-6" class="headerlink" title="子查询 - 6"></a>子查询 - 6</h3><p><strong>查询和 “李军” 同性别的所有同学 <code>name</code> 。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br></pre></td><td class="code"><pre><span class="line">-- 首先将李军的性别作为条件取出来</span><br><span class="line">SELECT sex FROM student WHERE name = '李军';</span><br><span class="line">+-----+</span><br><span class="line">| sex |</span><br><span class="line">+-----+</span><br><span class="line">| 男 |</span><br><span class="line">+-----+</span><br><span class="line"></span><br><span class="line">-- 根据性别查询 name 和 sex</span><br><span class="line">SELECT name, sex FROM student WHERE sex = (</span><br><span class="line"> SELECT sex FROM student WHERE name = '李军'</span><br><span class="line">);</span><br><span class="line">+-----------+-----+</span><br><span class="line">| name | sex |</span><br><span class="line">+-----------+-----+</span><br><span class="line">| 曾华 | 男 |</span><br><span class="line">| 匡明 | 男 |</span><br><span class="line">| 李军 | 男 |</span><br><span class="line">| 陆军 | 男 |</span><br><span class="line">| 王尼玛 | 男 |</span><br><span class="line">| 张全蛋 | 男 |</span><br><span class="line">| 赵铁柱 | 男 |</span><br><span class="line">| 张飞 | 男 |</span><br><span class="line">+-----------+-----+</span><br></pre></td></tr></table></figure><h3 id="子查询-7"><a href="#子查询-7" class="headerlink" title="子查询 - 7"></a>子查询 - 7</h3><p><strong>查询和 “李军” 同性别且同班的同学 <code>name</code> 。</strong></p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line">SELECT name, sex, class FROM student WHERE sex = (</span><br><span class="line"> SELECT sex FROM student WHERE name = '李军'</span><br><span class="line">) AND class = (</span><br><span class="line"> SELECT class FROM student WHERE name = '李军'</span><br><span class="line">);</span><br><span class="line">+-----------+-----+-------+</span><br><span class="line">| name | sex | class |</span><br><span class="line">+-----------+-----+-------+</span><br><span class="line">| 曾华 | 男 | 95033 |</span><br><span class="line">| 李军 | 男 | 95033 |</span><br><span class="line">| 王尼玛 | 男 | 95033 |</span><br><span class="line">+-----------+-----+-------+</span><br></pre></td></tr></table></figure><h3 id="子查询-8"><a href="#子查询-8" class="headerlink" title="子查询 - 8"></a>子查询 - 8</h3><p><strong>查询所有选修 “计算机导论” 课程的 “男” 同学成绩表。</strong></p><p>需要的 “计算机导论” 和性别为 “男” 的编号可以在 <code>course</code> 和 <code>student</code> 表中找到。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line">SELECT * FROM score WHERE c_no = (</span><br><span class="line"> SELECT no FROM course WHERE name = '计算机导论'</span><br><span class="line">) AND s_no IN (</span><br><span class="line"> SELECT no FROM student WHERE sex = '男'</span><br><span class="line">);</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| s_no | c_no | degree |</span><br><span class="line">+------+-------+--------+</span><br><span class="line">| 101 | 3-105 | 90 |</span><br><span class="line">| 102 | 3-105 | 91 |</span><br><span class="line">| 104 | 3-105 | 89 |</span><br><span class="line">| 109 | 3-105 | 76 |</span><br><span class="line">+------+-------+--------+</span><br></pre></td></tr></table></figure><h3 id="按等级查询"><a href="#按等级查询" class="headerlink" title="按等级查询"></a>按等级查询</h3><p>建立一个 <code>grade</code> 表代表学生的成绩等级,并插入数据:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br></pre></td><td class="code"><pre><span class="line">CREATE TABLE grade (</span><br><span class="line"> low INT(3),</span><br><span class="line"> upp INT(3),</span><br><span class="line"> grade char(1)</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">INSERT INTO grade VALUES (90, 100, 'A');</span><br><span class="line">INSERT INTO grade VALUES (80, 89, 'B');</span><br><span class="line">INSERT INTO grade VALUES (70, 79, 'C');</span><br><span class="line">INSERT INTO grade VALUES (60, 69, 'D');</span><br><span class="line">INSERT INTO grade VALUES (0, 59, 'E');</span><br><span class="line"></span><br><span class="line">SELECT * FROM grade;</span><br><span class="line">+------+------+-------+</span><br><span class="line">| low | upp | grade |</span><br><span class="line">+------+------+-------+</span><br><span class="line">| 90 | 100 | A |</span><br><span class="line">| 80 | 89 | B |</span><br><span class="line">| 70 | 79 | C |</span><br><span class="line">| 60 | 69 | D |</span><br><span class="line">| 0 | 59 | E |</span><br><span class="line">+------+------+-------+</span><br></pre></td></tr></table></figure><p><strong>查询所有学生的 <code>s_no</code> 、<code>c_no</code> 和 <code>grade</code> 列。</strong></p><p>思路是,使用区间 ( <code>BETWEEN</code> ) 查询,判断学生的成绩 ( <code>degree</code> ) 在 <code>grade</code> 表的 <code>low</code> 和 <code>upp</code> 之间。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br></pre></td><td class="code"><pre><span class="line">SELECT s_no, c_no, grade FROM score, grade</span><br><span class="line">WHERE degree BETWEEN low AND upp;</span><br><span class="line">+------+-------+-------+</span><br><span class="line">| s_no | c_no | grade |</span><br><span class="line">+------+-------+-------+</span><br><span class="line">| 101 | 3-105 | A |</span><br><span class="line">| 102 | 3-105 | A |</span><br><span class="line">| 103 | 3-105 | A |</span><br><span class="line">| 103 | 3-245 | B |</span><br><span class="line">| 103 | 6-166 | B |</span><br><span class="line">| 104 | 3-105 | B |</span><br><span class="line">| 105 | 3-105 | B |</span><br><span class="line">| 105 | 3-245 | C |</span><br><span class="line">| 105 | 6-166 | C |</span><br><span class="line">| 109 | 3-105 | C |</span><br><span class="line">| 109 | 3-245 | D |</span><br><span class="line">| 109 | 6-166 | B |</span><br><span class="line">+------+-------+-------+</span><br></pre></td></tr></table></figure><h3 id="连接查询"><a href="#连接查询" class="headerlink" title="连接查询"></a>连接查询</h3><p>准备用于测试连接查询的数据:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br></pre></td><td class="code"><pre><span class="line">CREATE DATABASE testJoin;</span><br><span class="line"></span><br><span class="line">CREATE TABLE person (</span><br><span class="line"> id INT,</span><br><span class="line"> name VARCHAR(20),</span><br><span class="line"> cardId INT</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">CREATE TABLE card (</span><br><span class="line"> id INT,</span><br><span class="line"> name VARCHAR(20)</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">INSERT INTO card VALUES (1, '饭卡'), (2, '建行卡'), (3, '农行卡'), (4, '工商卡'), (5, '邮政卡');</span><br><span class="line">SELECT * FROM card;</span><br><span class="line">+------+-----------+</span><br><span class="line">| id | name |</span><br><span class="line">+------+-----------+</span><br><span class="line">| 1 | 饭卡 |</span><br><span class="line">| 2 | 建行卡 |</span><br><span class="line">| 3 | 农行卡 |</span><br><span class="line">| 4 | 工商卡 |</span><br><span class="line">| 5 | 邮政卡 |</span><br><span class="line">+------+-----------+</span><br><span class="line"></span><br><span class="line">INSERT INTO person VALUES (1, '张三', 1), (2, '李四', 3), (3, '王五', 6);</span><br><span class="line">SELECT * FROM person;</span><br><span class="line">+------+--------+--------+</span><br><span class="line">| id | name | cardId |</span><br><span class="line">+------+--------+--------+</span><br><span class="line">| 1 | 张三 | 1 |</span><br><span class="line">| 2 | 李四 | 3 |</span><br><span class="line">| 3 | 王五 | 6 |</span><br><span class="line">+------+--------+--------+</span><br></pre></td></tr></table></figure><p>分析两张表发现,<code>person</code> 表并没有为 <code>cardId</code> 字段设置一个在 <code>card</code> 表中对应的 <code>id</code> 外键。如果设置了的话,<code>person</code> 中 <code>cardId</code> 字段值为 <code>6</code> 的行就插不进去,因为该 <code>cardId</code> 值在 <code>card</code> 表中并没有。</p><h4 id="内连接"><a href="#内连接" class="headerlink" title="内连接"></a>内连接</h4><p>要查询这两张表中有关系的数据,可以使用 <code>INNER JOIN</code> ( 内连接 ) 将它们连接在一起。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line">-- INNER JOIN: 表示为内连接,将两张表拼接在一起。</span><br><span class="line">-- on: 表示要执行某个条件。</span><br><span class="line">SELECT * FROM person INNER JOIN card on person.cardId = card.id;</span><br><span class="line">+------+--------+--------+------+-----------+</span><br><span class="line">| id | name | cardId | id | name |</span><br><span class="line">+------+--------+--------+------+-----------+</span><br><span class="line">| 1 | 张三 | 1 | 1 | 饭卡 |</span><br><span class="line">| 2 | 李四 | 3 | 3 | 农行卡 |</span><br><span class="line">+------+--------+--------+------+-----------+</span><br><span class="line"></span><br><span class="line">-- 将 INNER 关键字省略掉,结果也是一样的。</span><br><span class="line">-- SELECT * FROM person JOIN card on person.cardId = card.id;</span><br></pre></td></tr></table></figure><blockquote><p>注意:<code>card</code> 的整张表被连接到了右边。</p></blockquote><h4 id="左外连接"><a href="#左外连接" class="headerlink" title="左外连接"></a>左外连接</h4><p>完整显示左边的表 ( <code>person</code> ) ,右边的表如果符合条件就显示,不符合则补 <code>NULL</code> 。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line">-- LEFT JOIN 也叫做 LEFT OUTER JOIN,用这两种方式的查询结果是一样的。</span><br><span class="line">SELECT * FROM person LEFT JOIN card on person.cardId = card.id;</span><br><span class="line">+------+--------+--------+------+-----------+</span><br><span class="line">| id | name | cardId | id | name |</span><br><span class="line">+------+--------+--------+------+-----------+</span><br><span class="line">| 1 | 张三 | 1 | 1 | 饭卡 |</span><br><span class="line">| 2 | 李四 | 3 | 3 | 农行卡 |</span><br><span class="line">| 3 | 王五 | 6 | NULL | NULL |</span><br><span class="line">+------+--------+--------+------+-----------+</span><br></pre></td></tr></table></figure><h4 id="右外链接"><a href="#右外链接" class="headerlink" title="右外链接"></a>右外链接</h4><p>完整显示右边的表 ( <code>card</code> ) ,左边的表如果符合条件就显示,不符合则补 <code>NULL</code> 。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line">SELECT * FROM person RIGHT JOIN card on person.cardId = card.id;</span><br><span class="line">+------+--------+--------+------+-----------+</span><br><span class="line">| id | name | cardId | id | name |</span><br><span class="line">+------+--------+--------+------+-----------+</span><br><span class="line">| 1 | 张三 | 1 | 1 | 饭卡 |</span><br><span class="line">| 2 | 李四 | 3 | 3 | 农行卡 |</span><br><span class="line">| NULL | NULL | NULL | 2 | 建行卡 |</span><br><span class="line">| NULL | NULL | NULL | 4 | 工商卡 |</span><br><span class="line">| NULL | NULL | NULL | 5 | 邮政卡 |</span><br><span class="line">+------+--------+--------+------+-----------+</span><br></pre></td></tr></table></figure><h4 id="全外链接"><a href="#全外链接" class="headerlink" title="全外链接"></a>全外链接</h4><p>完整显示两张表的全部数据。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br></pre></td><td class="code"><pre><span class="line">-- MySQL 不支持这种语法的全外连接</span><br><span class="line">-- SELECT * FROM person FULL JOIN card on person.cardId = card.id;</span><br><span class="line">-- 出现错误:</span><br><span class="line">-- ERROR 1054 (42S22): Unknown column 'person.cardId' in 'on clause'</span><br><span class="line"></span><br><span class="line">-- MySQL全连接语法,使用 UNION 将两张表合并在一起。</span><br><span class="line">SELECT * FROM person LEFT JOIN card on person.cardId = card.id</span><br><span class="line">UNION</span><br><span class="line">SELECT * FROM person RIGHT JOIN card on person.cardId = card.id;</span><br><span class="line">+------+--------+--------+------+-----------+</span><br><span class="line">| id | name | cardId | id | name |</span><br><span class="line">+------+--------+--------+------+-----------+</span><br><span class="line">| 1 | 张三 | 1 | 1 | 饭卡 |</span><br><span class="line">| 2 | 李四 | 3 | 3 | 农行卡 |</span><br><span class="line">| 3 | 王五 | 6 | NULL | NULL |</span><br><span class="line">| NULL | NULL | NULL | 2 | 建行卡 |</span><br><span class="line">| NULL | NULL | NULL | 4 | 工商卡 |</span><br><span class="line">| NULL | NULL | NULL | 5 | 邮政卡 |</span><br><span class="line">+------+--------+--------+------+-----------+</span><br></pre></td></tr></table></figure><h2 id="事务"><a href="#事务" class="headerlink" title="事务"></a>事务</h2><p>在 MySQL 中,事务其实是一个最小的不可分割的工作单元。事务能够<strong>保证一个业务的完整性</strong>。</p><p>比如我们的银行转账:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">-- a -> -100</span><br><span class="line">UPDATE user set money = money - 100 WHERE name = 'a';</span><br><span class="line"></span><br><span class="line">-- b -> +100</span><br><span class="line">UPDATE user set money = money + 100 WHERE name = 'b';</span><br></pre></td></tr></table></figure><p>在实际项目中,假设只有一条 SQL 语句执行成功,而另外一条执行失败了,就会出现数据前后不一致。</p><p>因此,在执行多条有关联 SQL 语句时,<strong>事务</strong>可能会要求这些 SQL 语句要么同时执行成功,要么就都执行失败。</p><h3 id="如何控制事务-COMMIT-ROLLBACK"><a href="#如何控制事务-COMMIT-ROLLBACK" class="headerlink" title="如何控制事务 - COMMIT / ROLLBACK"></a>如何控制事务 - COMMIT / ROLLBACK</h3><p>在 MySQL 中,事务的<strong>自动提交</strong>状态默认是开启的。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">-- 查询事务的自动提交状态</span><br><span class="line">SELECT @@AUTOCOMMIT;</span><br><span class="line">+--------------+</span><br><span class="line">| @@AUTOCOMMIT |</span><br><span class="line">+--------------+</span><br><span class="line">| 1 |</span><br><span class="line">+--------------+</span><br></pre></td></tr></table></figure><p><strong>自动提交的作用</strong>:当我们执行一条 SQL 语句的时候,其产生的效果就会立即体现出来,且不能<strong>回滚</strong>。</p><p>什么是回滚?举个例子:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br></pre></td><td class="code"><pre><span class="line">CREATE DATABASE bank;</span><br><span class="line"></span><br><span class="line">USE bank;</span><br><span class="line"></span><br><span class="line">CREATE TABLE user (</span><br><span class="line"> id INT PRIMARY KEY,</span><br><span class="line"> name VARCHAR(20),</span><br><span class="line"> money INT</span><br><span class="line">);</span><br><span class="line"></span><br><span class="line">INSERT INTO user VALUES (1, 'a', 1000);</span><br><span class="line"></span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+------+-------+</span><br><span class="line">| 1 | a | 1000 |</span><br><span class="line">+----+------+-------+</span><br></pre></td></tr></table></figure><p>可以看到,在执行插入语句后数据立刻生效,原因是 MySQL 中的事务自动将它<strong>提交</strong>到了数据库中。那么所谓<strong>回滚</strong>的意思就是,撤销执行过的所有 SQL 语句,使其回滚到<strong>最后一次提交</strong>数据时的状态。</p><p>在 MySQL 中使用 <code>ROLLBACK</code> 执行回滚:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line">-- 回滚到最后一次提交</span><br><span class="line">ROLLBACK;</span><br><span class="line"></span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+------+-------+</span><br><span class="line">| 1 | a | 1000 |</span><br><span class="line">+----+------+-------+</span><br></pre></td></tr></table></figure><p>由于所有执行过的 SQL 语句都已经被提交过了,所以数据并没有发生回滚。那如何让数据可以发生回滚?</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line">-- 关闭自动提交</span><br><span class="line">SET AUTOCOMMIT = 0;</span><br><span class="line"></span><br><span class="line">-- 查询自动提交状态</span><br><span class="line">SELECT @@AUTOCOMMIT;</span><br><span class="line">+--------------+</span><br><span class="line">| @@AUTOCOMMIT |</span><br><span class="line">+--------------+</span><br><span class="line">| 0 |</span><br><span class="line">+--------------+</span><br></pre></td></tr></table></figure><p>将自动提交关闭后,测试数据回滚:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br></pre></td><td class="code"><pre><span class="line">INSERT INTO user VALUES (2, 'b', 1000);</span><br><span class="line"></span><br><span class="line">-- 关闭 AUTOCOMMIT 后,数据的变化是在一张虚拟的临时数据表中展示,</span><br><span class="line">-- 发生变化的数据并没有真正插入到数据表中。</span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+------+-------+</span><br><span class="line">| 1 | a | 1000 |</span><br><span class="line">| 2 | b | 1000 |</span><br><span class="line">+----+------+-------+</span><br><span class="line"></span><br><span class="line">-- 数据表中的真实数据其实还是:</span><br><span class="line">+----+------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+------+-------+</span><br><span class="line">| 1 | a | 1000 |</span><br><span class="line">+----+------+-------+</span><br><span class="line"></span><br><span class="line">-- 由于数据还没有真正提交,可以使用回滚</span><br><span class="line">ROLLBACK;</span><br><span class="line"></span><br><span class="line">-- 再次查询</span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+------+-------+</span><br><span class="line">| 1 | a | 1000 |</span><br><span class="line">+----+------+-------+</span><br></pre></td></tr></table></figure><p>那如何将虚拟的数据真正提交到数据库中?使用 <code>COMMIT</code> :</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br></pre></td><td class="code"><pre><span class="line">INSERT INTO user VALUES (2, 'b', 1000);</span><br><span class="line">-- 手动提交数据(持久性),</span><br><span class="line">-- 将数据真正提交到数据库中,执行后不能再回滚提交过的数据。</span><br><span class="line">COMMIT;</span><br><span class="line"></span><br><span class="line">-- 提交后测试回滚</span><br><span class="line">ROLLBACK;</span><br><span class="line"></span><br><span class="line">-- 再次查询(回滚无效了)</span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+------+-------+</span><br><span class="line">| 1 | a | 1000 |</span><br><span class="line">| 2 | b | 1000 |</span><br><span class="line">+----+------+-------+</span><br></pre></td></tr></table></figure><blockquote><p><strong>总结</strong></p><ol><li><p><strong>自动提交</strong></p><ul><li><p>查看自动提交状态:<code>SELECT @@AUTOCOMMIT</code> ;</p></li><li><p>设置自动提交状态:<code>SET AUTOCOMMIT = 0</code> 。</p></li></ul></li><li><p><strong>手动提交</strong></p><p><code>@@AUTOCOMMIT = 0</code> 时,使用 <code>COMMIT</code> 命令提交事务。</p></li><li><p><strong>事务回滚</strong></p><p><code>@@AUTOCOMMIT = 0</code> 时,使用 <code>ROLLBACK</code> 命令回滚事务。</p></li></ol></blockquote><p><strong>事务的实际应用</strong>,让我们再回到银行转账项目:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line">-- 转账</span><br><span class="line">UPDATE user set money = money - 100 WHERE name = 'a';</span><br><span class="line"></span><br><span class="line">-- 到账</span><br><span class="line">UPDATE user set money = money + 100 WHERE name = 'b';</span><br><span class="line"></span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+------+-------+</span><br><span class="line">| 1 | a | 900 |</span><br><span class="line">| 2 | b | 1100 |</span><br><span class="line">+----+------+-------+</span><br></pre></td></tr></table></figure><p>这时假设在转账时发生了意外,就可以使用 <code>ROLLBACK</code> 回滚到最后一次提交的状态:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line">-- 假设转账发生了意外,需要回滚。</span><br><span class="line">ROLLBACK;</span><br><span class="line"></span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+------+-------+</span><br><span class="line">| 1 | a | 1000 |</span><br><span class="line">| 2 | b | 1000 |</span><br><span class="line">+----+------+-------+</span><br></pre></td></tr></table></figure><p>这时我们又回到了发生意外之前的状态,也就是说,事务给我们提供了一个可以反悔的机会。假设数据没有发生意外,这时可以手动将数据真正提交到数据表中:<code>COMMIT</code> 。</p><h3 id="手动开启事务-BEGIN-START-TRANSACTION"><a href="#手动开启事务-BEGIN-START-TRANSACTION" class="headerlink" title="手动开启事务 - BEGIN / START TRANSACTION"></a>手动开启事务 - BEGIN / START TRANSACTION</h3><p>事务的默认提交被开启 ( <code>@@AUTOCOMMIT = 1</code> ) 后,此时就不能使用事务回滚了。但是我们还可以手动开启一个事务处理事件,使其可以发生回滚:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br></pre></td><td class="code"><pre><span class="line">-- 使用 BEGIN 或者 START TRANSACTION 手动开启一个事务</span><br><span class="line">-- START TRANSACTION;</span><br><span class="line">BEGIN;</span><br><span class="line">UPDATE user set money = money - 100 WHERE name = 'a';</span><br><span class="line">UPDATE user set money = money + 100 WHERE name = 'b';</span><br><span class="line"></span><br><span class="line">-- 由于手动开启的事务没有开启自动提交,</span><br><span class="line">-- 此时发生变化的数据仍然是被保存在一张临时表中。</span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+------+-------+</span><br><span class="line">| 1 | a | 900 |</span><br><span class="line">| 2 | b | 1100 |</span><br><span class="line">+----+------+-------+</span><br><span class="line"></span><br><span class="line">-- 测试回滚</span><br><span class="line">ROLLBACK;</span><br><span class="line"></span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+------+-------+</span><br><span class="line">| 1 | a | 1000 |</span><br><span class="line">| 2 | b | 1000 |</span><br><span class="line">+----+------+-------+</span><br></pre></td></tr></table></figure><p>仍然使用 <code>COMMIT</code> 提交数据,提交后无法再发生本次事务的回滚。</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line">BEGIN;</span><br><span class="line">UPDATE user set money = money - 100 WHERE name = 'a';</span><br><span class="line">UPDATE user set money = money + 100 WHERE name = 'b';</span><br><span class="line"></span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+------+-------+</span><br><span class="line">| 1 | a | 900 |</span><br><span class="line">| 2 | b | 1100 |</span><br><span class="line">+----+------+-------+</span><br><span class="line"></span><br><span class="line">-- 提交数据</span><br><span class="line">COMMIT;</span><br><span class="line"></span><br><span class="line">-- 测试回滚(无效,因为表的数据已经被提交)</span><br><span class="line">ROLLBACK;</span><br></pre></td></tr></table></figure><h3 id="事务的-ACID-特征与使用"><a href="#事务的-ACID-特征与使用" class="headerlink" title="事务的 ACID 特征与使用"></a>事务的 ACID 特征与使用</h3><p><strong>事务的四大特征:</strong></p><ul><li><strong>A 原子性</strong>:事务是最小的单位,不可以再分割;</li><li><strong>C 一致性</strong>:要求同一事务中的 SQL 语句,必须保证同时成功或者失败;</li><li><strong>I 隔离性</strong>:事务1 和 事务2 之间是具有隔离性的;</li><li><strong>D 持久性</strong>:事务一旦结束 ( <code>COMMIT</code> ) ,就不可以再返回了 ( <code>ROLLBACK</code> ) 。</li></ul><h3 id="事务的隔离性"><a href="#事务的隔离性" class="headerlink" title="事务的隔离性"></a>事务的隔离性</h3><p><strong>事务的隔离性可分为四种 ( 性能从低到高 )</strong> :</p><ol><li><p><strong>READ UNCOMMITTED ( 读取未提交 )</strong></p><p>如果有多个事务,那么任意事务都可以看见其他事务的<strong>未提交数据</strong>。</p></li><li><p><strong>READ COMMITTED ( 读取已提交 )</strong></p><p>只能读取到其他事务<strong>已经提交的数据</strong>。</p></li><li><p><strong>REPEATABLE READ ( 可被重复读 )</strong></p><p>如果有多个连接都开启了事务,那么事务之间不能共享数据记录,否则只能共享已提交的记录。</p></li><li><p><strong>SERIALIZABLE ( 串行化 )</strong></p><p>所有的事务都会按照<strong>固定顺序执行</strong>,执行完一个事务后再继续执行下一个事务的<strong>写入操作</strong>。</p></li></ol><p>查看当前数据库的默认隔离级别:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line">-- MySQL 8.x, GLOBAL 表示系统级别,不加表示会话级别。</span><br><span class="line">SELECT @@GLOBAL.TRANSACTION_ISOLATION;</span><br><span class="line">SELECT @@TRANSACTION_ISOLATION;</span><br><span class="line">+--------------------------------+</span><br><span class="line">| @@GLOBAL.TRANSACTION_ISOLATION |</span><br><span class="line">+--------------------------------+</span><br><span class="line">| REPEATABLE-READ | -- MySQL的默认隔离级别,可以重复读。</span><br><span class="line">+--------------------------------+</span><br><span class="line"></span><br><span class="line">-- MySQL 5.x</span><br><span class="line">SELECT @@GLOBAL.TX_ISOLATION;</span><br><span class="line">SELECT @@TX_ISOLATION;</span><br></pre></td></tr></table></figure><p>修改隔离级别:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line">-- 设置系统隔离级别,LEVEL 后面表示要设置的隔离级别 (READ UNCOMMITTED)。</span><br><span class="line">SET GLOBAL TRANSACTION ISOLATION LEVEL READ UNCOMMITTED;</span><br><span class="line"></span><br><span class="line">-- 查询系统隔离级别,发现已经被修改。</span><br><span class="line">SELECT @@GLOBAL.TRANSACTION_ISOLATION;</span><br><span class="line">+--------------------------------+</span><br><span class="line">| @@GLOBAL.TRANSACTION_ISOLATION |</span><br><span class="line">+--------------------------------+</span><br><span class="line">| READ-UNCOMMITTED |</span><br><span class="line">+--------------------------------+</span><br></pre></td></tr></table></figure><h4 id="脏读"><a href="#脏读" class="headerlink" title="脏读"></a>脏读</h4><p>测试 <strong>READ UNCOMMITTED ( 读取未提交 )</strong> 的隔离性:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br></pre></td><td class="code"><pre><span class="line">INSERT INTO user VALUES (3, '小明', 1000);</span><br><span class="line">INSERT INTO user VALUES (4, '淘宝店', 1000);</span><br><span class="line"></span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| 1 | a | 900 |</span><br><span class="line">| 2 | b | 1100 |</span><br><span class="line">| 3 | 小明 | 1000 |</span><br><span class="line">| 4 | 淘宝店 | 1000 |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line"></span><br><span class="line">-- 开启一个事务操作数据</span><br><span class="line">-- 假设小明在淘宝店买了一双800块钱的鞋子:</span><br><span class="line">START TRANSACTION;</span><br><span class="line">UPDATE user SET money = money - 800 WHERE name = '小明';</span><br><span class="line">UPDATE user SET money = money + 800 WHERE name = '淘宝店';</span><br><span class="line"></span><br><span class="line">-- 然后淘宝店在另一方查询结果,发现钱已到账。</span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| 1 | a | 900 |</span><br><span class="line">| 2 | b | 1100 |</span><br><span class="line">| 3 | 小明 | 200 |</span><br><span class="line">| 4 | 淘宝店 | 1800 |</span><br><span class="line">+----+-----------+-------+</span><br></pre></td></tr></table></figure><p>由于小明的转账是在新开启的事务上进行操作的,而该操作的结果是可以被其他事务(另一方的淘宝店)看见的,因此淘宝店的查询结果是正确的,淘宝店确认到账。但就在这时,如果小明在它所处的事务上又执行了 <code>ROLLBACK</code> 命令,会发生什么?</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line">-- 小明所处的事务</span><br><span class="line">ROLLBACK;</span><br><span class="line"></span><br><span class="line">-- 此时无论对方是谁,如果再去查询结果就会发现:</span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| 1 | a | 900 |</span><br><span class="line">| 2 | b | 1100 |</span><br><span class="line">| 3 | 小明 | 1000 |</span><br><span class="line">| 4 | 淘宝店 | 1000 |</span><br><span class="line">+----+-----------+-------+</span><br></pre></td></tr></table></figure><p>这就是所谓的<strong>脏读</strong>,一个事务读取到另外一个事务还未提交的数据。这在实际开发中是不允许出现的。</p><h4 id="读取已提交"><a href="#读取已提交" class="headerlink" title="读取已提交"></a>读取已提交</h4><p>把隔离级别设置为 <strong>READ COMMITTED</strong> :</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">SET GLOBAL TRANSACTION ISOLATION LEVEL READ COMMITTED;</span><br><span class="line">SELECT @@GLOBAL.TRANSACTION_ISOLATION;</span><br><span class="line">+--------------------------------+</span><br><span class="line">| @@GLOBAL.TRANSACTION_ISOLATION |</span><br><span class="line">+--------------------------------+</span><br><span class="line">| READ-COMMITTED |</span><br><span class="line">+--------------------------------+</span><br></pre></td></tr></table></figure><p>这样,再有新的事务连接进来时,它们就只能查询到已经提交过的事务数据了。但是对于当前事务来说,它们看到的还是未提交的数据,例如:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br></pre></td><td class="code"><pre><span class="line">-- 正在操作数据事务(当前事务)</span><br><span class="line">START TRANSACTION;</span><br><span class="line">UPDATE user SET money = money - 800 WHERE name = '小明';</span><br><span class="line">UPDATE user SET money = money + 800 WHERE name = '淘宝店';</span><br><span class="line"></span><br><span class="line">-- 虽然隔离级别被设置为了 READ COMMITTED,但在当前事务中,</span><br><span class="line">-- 它看到的仍然是数据表中临时改变数据,而不是真正提交过的数据。</span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| 1 | a | 900 |</span><br><span class="line">| 2 | b | 1100 |</span><br><span class="line">| 3 | 小明 | 200 |</span><br><span class="line">| 4 | 淘宝店 | 1800 |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line"></span><br><span class="line"></span><br><span class="line">-- 假设此时在远程开启了一个新事务,连接到数据库。</span><br><span class="line">$ mysql -u root -p12345612</span><br><span class="line"></span><br><span class="line">-- 此时远程连接查询到的数据只能是已经提交过的</span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| 1 | a | 900 |</span><br><span class="line">| 2 | b | 1100 |</span><br><span class="line">| 3 | 小明 | 1000 |</span><br><span class="line">| 4 | 淘宝店 | 1000 |</span><br><span class="line">+----+-----------+-------+</span><br></pre></td></tr></table></figure><p>但是这样还有问题,那就是假设一个事务在操作数据时,其他事务干扰了这个事务的数据。例如:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br></pre></td><td class="code"><pre><span class="line">-- 小张在查询数据的时候发现:</span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| 1 | a | 900 |</span><br><span class="line">| 2 | b | 1100 |</span><br><span class="line">| 3 | 小明 | 200 |</span><br><span class="line">| 4 | 淘宝店 | 1800 |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line"></span><br><span class="line">-- 在小张求表的 money 平均值之前,小王做了一个操作:</span><br><span class="line">START TRANSACTION;</span><br><span class="line">INSERT INTO user VALUES (5, 'c', 100);</span><br><span class="line">COMMIT;</span><br><span class="line"></span><br><span class="line">-- 此时表的真实数据是:</span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| 1 | a | 900 |</span><br><span class="line">| 2 | b | 1100 |</span><br><span class="line">| 3 | 小明 | 1000 |</span><br><span class="line">| 4 | 淘宝店 | 1000 |</span><br><span class="line">| 5 | c | 100 |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line"></span><br><span class="line">-- 这时小张再求平均值的时候,就会出现计算不相符合的情况:</span><br><span class="line">SELECT AVG(money) FROM user;</span><br><span class="line">+------------+</span><br><span class="line">| AVG(money) |</span><br><span class="line">+------------+</span><br><span class="line">| 820.0000 |</span><br><span class="line">+------------+</span><br></pre></td></tr></table></figure><p>虽然 <strong>READ COMMITTED</strong> 让我们只能读取到其他事务已经提交的数据,但还是会出现问题,就是<strong>在读取同一个表的数据时,可能会发生前后不一致的情况。</strong>这被称为<strong>不可重复读现象 ( READ COMMITTED )</strong> 。</p><h4 id="幻读"><a href="#幻读" class="headerlink" title="幻读"></a>幻读</h4><p>将隔离级别设置为 <strong>REPEATABLE READ ( 可被重复读取 )</strong> :</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">SET GLOBAL TRANSACTION ISOLATION LEVEL REPEATABLE READ;</span><br><span class="line">SELECT @@GLOBAL.TRANSACTION_ISOLATION;</span><br><span class="line">+--------------------------------+</span><br><span class="line">| @@GLOBAL.TRANSACTION_ISOLATION |</span><br><span class="line">+--------------------------------+</span><br><span class="line">| REPEATABLE-READ |</span><br><span class="line">+--------------------------------+</span><br></pre></td></tr></table></figure><p>测试 <strong>REPEATABLE READ</strong> ,假设在两个不同的连接上分别执行 <code>START TRANSACTION</code> :</p><figure class="highlight sql"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">-- 小张 - 成都</span></span><br><span class="line"><span class="keyword">START</span> TRANSACTION;</span><br><span class="line"><span class="keyword">INSERT</span> <span class="keyword">INTO</span> <span class="keyword">user</span> <span class="keyword">VALUES</span> (<span class="number">6</span>, <span class="string">'d'</span>, <span class="number">1000</span>);</span><br><span class="line"></span><br><span class="line"><span class="comment">-- 小王 - 北京</span></span><br><span class="line"><span class="keyword">START</span> TRANSACTION;</span><br><span class="line"></span><br><span class="line"><span class="comment">-- 小张 - 成都</span></span><br><span class="line"><span class="keyword">COMMIT</span>;</span><br></pre></td></tr></table></figure><p>当前事务开启后,没提交之前,查询不到,提交后可以被查询到。但是,在提交之前其他事务被开启了,那么在这条事务线上,就不会查询到当前有操作事务的连接。相当于开辟出一条单独的线程。</p><p>无论小张是否执行过 <code>COMMIT</code> ,在小王这边,都不会查询到小张的事务记录,而是只会查询到自己所处事务的记录:</p><figure class="highlight sql"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">SELECT</span> <span class="operator">*</span> <span class="keyword">FROM</span> <span class="keyword">user</span>;</span><br><span class="line"><span class="operator">+</span><span class="comment">----+-----------+-------+</span></span><br><span class="line"><span class="operator">|</span> id <span class="operator">|</span> name <span class="operator">|</span> money <span class="operator">|</span></span><br><span class="line"><span class="operator">+</span><span class="comment">----+-----------+-------+</span></span><br><span class="line"><span class="operator">|</span> <span class="number">1</span> <span class="operator">|</span> a <span class="operator">|</span> <span class="number">900</span> <span class="operator">|</span></span><br><span class="line"><span class="operator">|</span> <span class="number">2</span> <span class="operator">|</span> b <span class="operator">|</span> <span class="number">1100</span> <span class="operator">|</span></span><br><span class="line"><span class="operator">|</span> <span class="number">3</span> <span class="operator">|</span> 小明 <span class="operator">|</span> <span class="number">1000</span> <span class="operator">|</span></span><br><span class="line"><span class="operator">|</span> <span class="number">4</span> <span class="operator">|</span> 淘宝店 <span class="operator">|</span> <span class="number">1000</span> <span class="operator">|</span></span><br><span class="line"><span class="operator">|</span> <span class="number">5</span> <span class="operator">|</span> c <span class="operator">|</span> <span class="number">100</span> <span class="operator">|</span></span><br><span class="line"><span class="operator">+</span><span class="comment">----+-----------+-------+</span></span><br></pre></td></tr></table></figure><p>这是<strong>因为小王在此之前开启了一个新的事务 ( <code>START TRANSACTION</code> )</strong>,那么<strong>在他的这条新事务的线上,跟其他事务是没有联系的</strong>,也就是说,此时如果其他事务正在操作数据,它是不知道的。</p><p>然而事实是,在真实的数据表中,小张已经插入了一条数据。但是小王此时并不知道,也插入了同一条数据,会发生什么呢?</p><figure class="highlight sql"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">INSERT</span> <span class="keyword">INTO</span> <span class="keyword">user</span> <span class="keyword">VALUES</span> (<span class="number">6</span>, <span class="string">'d'</span>, <span class="number">1000</span>);</span><br><span class="line"><span class="comment">-- ERROR 1062 (23000): Duplicate entry '6' for key 'PRIMARY'</span></span><br></pre></td></tr></table></figure><p>报错了,操作被告知已存在主键为 <code>6</code> 的字段。这种现象也被称为<strong>幻读,一个事务提交的数据,不能被其他事务读取到</strong>。</p><h4 id="串行化"><a href="#串行化" class="headerlink" title="串行化"></a>串行化</h4><p>顾名思义,就是所有事务的<strong>写入操作</strong>全都是串行化的。什么意思?把隔离级别修改成 <strong>SERIALIZABLE</strong> :</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">SET GLOBAL TRANSACTION ISOLATION LEVEL SERIALIZABLE;</span><br><span class="line">SELECT @@GLOBAL.TRANSACTION_ISOLATION;</span><br><span class="line">+--------------------------------+</span><br><span class="line">| @@GLOBAL.TRANSACTION_ISOLATION |</span><br><span class="line">+--------------------------------+</span><br><span class="line">| SERIALIZABLE |</span><br><span class="line">+--------------------------------+</span><br></pre></td></tr></table></figure><p>还是拿小张和小王来举例:</p><figure class="highlight plaintext"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br></pre></td><td class="code"><pre><span class="line">-- 小张 - 成都</span><br><span class="line">START TRANSACTION;</span><br><span class="line"></span><br><span class="line">-- 小王 - 北京</span><br><span class="line">START TRANSACTION;</span><br><span class="line"></span><br><span class="line">-- 开启事务之前先查询表,准备操作数据。</span><br><span class="line">SELECT * FROM user;</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| id | name | money |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line">| 1 | a | 900 |</span><br><span class="line">| 2 | b | 1100 |</span><br><span class="line">| 3 | 小明 | 1000 |</span><br><span class="line">| 4 | 淘宝店 | 1000 |</span><br><span class="line">| 5 | c | 100 |</span><br><span class="line">| 6 | d | 1000 |</span><br><span class="line">+----+-----------+-------+</span><br><span class="line"></span><br><span class="line">-- 发现没有 7 号王小花,于是插入一条数据:</span><br><span class="line">INSERT INTO user VALUES (7, '王小花', 1000);</span><br></pre></td></tr></table></figure><p>此时会发生什么呢?由于现在的隔离级别是 <strong>SERIALIZABLE ( 串行化 )</strong> ,串行化的意思就是:假设把所有的事务都放在一个串行的队列中,那么所有的事务都会按照<strong>固定顺序执行</strong>,执行完一个事务后再继续执行下一个事务的<strong>写入操作</strong> ( <strong>这意味着队列中同时只能执行一个事务的写入操作</strong> ) 。</p><p>根据这个解释,小王在插入数据时,会出现等待状态,直到小张执行 <code>COMMIT</code> 结束它所处的事务,或者出现等待超时。</p>]]></content>
<categories>
<category> 编程 </category>
</categories>
<tags>
<tag> MySQL </tag>
</tags>
</entry>
<entry>
<title>Hello,World!</title>
<link href="/posts/0.html"/>
<url>/posts/0.html</url>
<content type="html"><![CDATA[<!-- markdownlint-disable MD025 MD026 --><h1 id="Hello,World"><a href="#Hello,World" class="headerlink" title="Hello,World!"></a>Hello,World!</h1>]]></content>
<categories>
<category> 日常 </category>
</categories>
<tags>
<tag> Hello,World </tag>
</tags>
</entry>
<entry>
<title>分类</title>
<link href="/categories/index.html"/>
<url>/categories/index.html</url>
<content type="html"><![CDATA[]]></content>
</entry>
<entry>
<title></title>
<link href="/css/custom.css"/>
<url>/css/custom.css</url>
<content type="html"><![CDATA[/* @font-face { font-family: Candyhome; src: url(https://npm.elemecdn.com/[email protected]/fonts/Candyhome.ttf); font-display: swap; font-weight: lighter;} */@font-face { font-family: ZhuZiAYuanJWD; src: url(https://npm.elemecdn.com/[email protected]/fonts/ZhuZiAWan.woff2); font-display: swap; font-weight: lighter; } div#menus { font-family: 'ZhuZiAYuanJWD'; } h1#site-title { font-family: ZhuZiAYuanJWD; font-size: 3em !important; } a.article-title, a.blog-slider__title, a.categoryBar-list-link, h1.post-title { font-family: ZhuZiAYuanJWD; } .iconfont { font-family: 'iconfont' !important; font-size: 3em; /* 可以定义图标大小 */ font-style: normal; -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; } /* 时间轴生肖icon */ svg.icon { /* 这里定义svg.icon,避免和Butterfly自带的note标签冲突 */ width: 1em; height: 1em; /* width和height定义图标的默认宽度和高度*/ vertical-align: -0.15em; fill: currentColor; overflow: hidden; } .icon-zhongbiao::before { color: #f7c768; } /* bilibli番剧插件 */ .bangumi-active { background: #dbecfe !important; border-radius: 10px !important; } a.bangumi-tab:hover { text-decoration: none !important; } .bangumi-button:hover { background: #dbecfe !important; border-radius: 10px !important; } a.bangumi-button.bangumi-nextpage:hover { text-decoration: none !important; } .bangumi-button { padding: 5px 10px !important; } a.bangumi-tab { padding: 5px 10px !important; } svg.icon.faa-tada { font-size: 1.1em; } /* 解决artitalk的图标问题 */ #uploadSource > svg { width: 1.19em; height: 1.5em; } /*top-img黑色透明玻璃效果移除,不建议加,除非你执着于完全一图流或者背景图对比色明显 */ #page-header:not(.not-top-img):before { background-color: transparent !important; } /* 首页文章卡片 */ #recent-posts > .recent-post-item { background: rgba(255, 255, 255, 0.9); } /* 首页侧栏卡片 */ #aside-content .card-widget { background: rgba(255, 255, 255, 0.9); } /* 文章页面正文背景 */ div#post { background: rgba(255, 255, 255, 0.9); } /* 分页页面 */ div#page { background: rgba(255, 255, 255, 0.9); } /* 归档页面 */ div#archive { background: rgba(255, 255, 255, 0.9); } /* 标签页面 */ div#tag { background: rgba(255, 255, 255, 0.9); } /* 分类页面 */ div#category { background: rgba(255, 255, 255, 0.9); } /*夜间模式伪类遮罩层透明*/ [data-theme='dark'] #recent-posts > .recent-post-item { background: #121212; } [data-theme='dark'] .card-widget { background: #121212 !important; } [data-theme='dark'] div#post { background: #121212 !important; } [data-theme='dark'] div#tag { background: #121212 !important; } [data-theme='dark'] div#archive { background: #121212 !important; } [data-theme='dark'] div#page { background: #121212 !important; } [data-theme='dark'] div#category { background: #121212 !important; } [data-theme='dark'] div#category { background: transparent !important; } /* 页脚透明 */ #footer { background: transparent !important; } /* 头图透明 */ #page-header { background: transparent !important; } #rightside > div > button { border-radius: 5px; } /* 滚动条 */ ::-webkit-scrollbar { width: 10px; height: 10px; } ::-webkit-scrollbar-thumb { background-color: #49b1f5; border-radius: 2em; } ::-webkit-scrollbar-corner { background-color: transparent; } ::-moz-selection { color: #fff; background-color: #49b1f5; } /* 音乐播放器 */ /* .aplayer .aplayer-lrc { display: none !important; } */ .aplayer.aplayer-fixed.aplayer-narrow .aplayer-body { left: -66px !important; transition: all 0.3s; /* 默认情况下缩进左侧66px,只留一点箭头部分 */ } .aplayer.aplayer-fixed.aplayer-narrow .aplayer-body:hover { left: 0 !important; transition: all 0.3s; /* 鼠标悬停是左侧缩进归零,完全显示按钮 */ } .aplayer.aplayer-fixed { z-index: 999999 !important; } /* 评论框 */ .vwrap { box-shadow: 2px 2px 5px #bbb; background: rgba(255, 255, 255, 0.3); border-radius: 8px; padding: 30px; margin: 30px 0px 30px 0px; } /* 设置评论框 */ .vcard { box-shadow: 2px 2px 5px #bbb; background: rgba(255, 255, 255, 0.3); border-radius: 8px; padding: 30px; margin: 30px 0px 0px 0px; } /* 鼠标图标 */ body { cursor: url('/img/arrow.cur'), auto; } a, [type='button']:not(:disabled), [type='reset']:not(:disabled), [type='submit']:not(:disabled), button:not(:disabled) { cursor: url('/img/x2.cur'), auto !important; } /* md网站下划线 */ #article-container a:hover { text-decoration: none !important; } #article-container #hpp_talk p img { display: inline; } /* 404页面 */ #error-wrap { position: absolute; top: 40%; right: 0; left: 0; margin: 0 auto; padding: 0 1rem; max-width: 1000px; transform: translate(0, -50%); } #error-wrap .error-content { display: flex; flex-direction: row; justify-content: center; align-items: center; margin: 0 1rem; height: 18rem; border-radius: 8px; background: var(--card-bg); box-shadow: var(--card-box-shadow); transition: all 0.3s; } #error-wrap .error-content .error-img { box-flex: 1; flex: 1; height: 100%; border-top-left-radius: 8px; border-bottom-left-radius: 8px; background-color: #49b1f5; background-position: center; background-size: cover; } #error-wrap .error-content .error-info { box-flex: 1; flex: 1; padding: 0.5rem; text-align: center; font-size: 14px; font-family: Titillium Web, 'PingFang SC', 'Hiragino Sans GB', 'Microsoft JhengHei', 'Microsoft YaHei', sans-serif; } #error-wrap .error-content .error-info .error_title { margin-top: -4rem; font-size: 9em; } #error-wrap .error-content .error-info .error_subtitle { margin-top: -3.5rem; word-break: break-word; font-size: 1.6em; } #error-wrap .error-content .error-info a { display: inline-block; margin-top: 0.5rem; padding: 0.3rem 1.5rem; background: var(--btn-bg); color: var(--btn-color); } #body-wrap.error .aside-list { display: flex; flex-direction: row; flex-wrap: nowrap; bottom: 0px; position: absolute; padding: 1rem; width: 100%; overflow: scroll; } #body-wrap.error .aside-list .aside-list-group { display: flex; flex-direction: row; flex-wrap: nowrap; max-width: 1200px; margin: 0 auto; } #body-wrap.error .aside-list .aside-list-item { padding: 0.5rem; } #body-wrap.error .aside-list .aside-list-item img { width: 100%; object-fit: cover; border-radius: 12px; } #body-wrap.error .aside-list .aside-list-item .thumbnail { overflow: hidden; width: 230px; height: 143px; background: var(--heo-card-bg); display: flex; } #body-wrap.error .aside-list .aside-list-item .content .title { -webkit-line-clamp: 2; overflow: hidden; display: -webkit-box; -webkit-box-orient: vertical; line-height: 1.5; justify-content: center; align-items: flex-end; align-content: center; padding-top: 0.5rem; color: white; } #body-wrap.error .aside-list .aside-list-item .content time { display: none; } /* 代码框主题 */ #article-container figure.highlight { border-radius: 10px; }]]></content>
</entry>
<entry>
<title></title>
<link href="/js/gitcalendar.js"/>
<url>/js/gitcalendar.js</url>
<content type="html"><![CDATA[function GitCalendarInit(git_gitapiurl, git_color, git_user) { // 由于 git_gitapiurl 为https://python-github-calendar-api-lake-six.vercel.app/api?Alleyway-boop // 我们需要将 修改参数为 https://python-github-calendar-api-lake-six.vercel.app/api?user=Alleyway-boop 这样的形式 保留?前面的部分,后面的部分移除 git_gitapiurl = git_gitapiurl.split('?')[0] + '?user=' + git_user if (document.getElementById('git_container')) { var git_canlendar = (git_user, git_gitapiurl, git_color) => { var git_fixed = 'fixed'; var git_px = 'px'; var git_month = ['一月', '二月', '三月', '四月', '五月', '六月', '七月', '八月', '九月', '十月', '十一月', '十二月']; var git_monthchange = []; var git_oneyearbeforeday = ''; var git_thisday = ''; var git_amonthago = ''; var git_aweekago = ''; var git_weekdatacore = 0; var git_datacore = 0; var git_total = 0; var git_datadate = ''; var git_git_data = []; var git_positionplusdata = []; var git_firstweek = []; var git_lastweek = []; var git_beforeweek = []; var git_thisweekdatacore = 0; var git_mounthbeforeday = 0; var git_mounthfirstindex = 0; var git_crispedges = 'crispedges'; var git_thisdayindex = 0; var git_amonthagoindex = 0; var git_amonthagoweek = []; var git_firstdate = []; var git_first2date = []; var git_montharrbefore = []; var git_monthindex = 0; var retinaCanvas = (canvas, context, ratio) => { if (ratio > 1) { var canvasWidth = canvas.width; var canvasHeight = canvas.height; canvas.width = canvasWidth * ratio; canvas.height = canvasHeight * ratio; canvas.style.width = '100%'; canvas.style.height = canvasHeight + 'px'; context.scale(ratio, ratio); } } var responsiveChart = () => { if (document.getElementById("gitcanvas")) { var git_tooltip_container = document.getElementById('git_tooltip_container'); var ratio = window.devicePixelRatio || 1 var git_x = ''; var git_y = ''; var git_span1 = ''; var git_span2 = ''; var git_calendar_c = document.getElementById("gitcanvas"); git_calendar_c.style.width = '100%'; git_calendar_c.style.height = ''; var cmessage = document.getElementById("gitmessage"); var git_calendar_ctx = git_calendar_c.getContext("2d"); width = git_calendar_c.width = document.getElementById("gitcalendarcanvasbox").offsetWidth; height = git_calendar_c.height = 9 * 0.96 * git_calendar_c.width / git_data.length; retinaCanvas(git_calendar_c, git_calendar_ctx, ratio) var linemaxwitdh = height / 9; var lineminwitdh = 0.8 * linemaxwitdh; var setposition = { x: 0.02 * width, y: 0.025 * width }; for (var week in git_data) { weekdata = git_data[week]; for (var day in weekdata) { var dataitem = { date: "", count: "", x: 0, y: 0 }; git_positionplusdata.push(dataitem); git_calendar_ctx.fillStyle = git_thiscolor(git_color, weekdata[day].count); setposition.y = Math.round(setposition.y * 100) / 100; dataitem.date = weekdata[day].date; dataitem.count = weekdata[day].count; dataitem.x = setposition.x; dataitem.y = setposition.y; git_calendar_ctx.fillRect(setposition.x, setposition.y, lineminwitdh, lineminwitdh); setposition.y = setposition.y + linemaxwitdh } setposition.y = 0.025 * width; setposition.x = setposition.x + linemaxwitdh; } if (document.body.clientWidth > 700) { git_calendar_ctx.font = "600 Arial"; git_calendar_ctx.fillStyle = '#aaa'; git_calendar_ctx.fillText("日", 0, 1.9 * linemaxwitdh); git_calendar_ctx.fillText("二", 0, 3.9 * linemaxwitdh); git_calendar_ctx.fillText("四", 0, 5.9 * linemaxwitdh); git_calendar_ctx.fillText("六", 0, 7.9 * linemaxwitdh); var monthindexlist = git_calendar_c.width / 24; for (var index in git_monthchange) { git_calendar_ctx.fillText(git_monthchange[index], monthindexlist, 0.7 * linemaxwitdh); monthindexlist = monthindexlist + git_calendar_c.width / 12 } } git_calendar_c.onmousemove = function (event) { if (document.querySelector('.gitmessage')) { git_tooltip_container.innerHTML = "" } getMousePos(git_calendar_c, event) }; git_tooltip_container.onmousemove = function (event) { if (document.querySelector('.gitmessage')) { git_tooltip_container.innerHTML = "" } }; var getMousePos = (canvas, event) => { var rect = canvas.getBoundingClientRect(); var x = event.clientX - rect.left * (canvas.width / rect.width); var y = event.clientY - rect.top * (canvas.height / rect.height); for (var item of git_positionplusdata) { var lenthx = x - item.x; var lenthy = y - item.y; if (0 < lenthx && lenthx < lineminwitdh) { if (0 < lenthy && lenthy < lineminwitdh) { git_span1 = item.date; git_span2 = item.count; git_x = event.clientX - 100; git_y = event.clientY - 60; html = tooltip_html(git_x, git_y, git_span1, git_span2); append_div_gitcalendar(git_tooltip_container, html) } } } } } } var addlastmonth = () => { if (git_thisdayindex === 0) { thisweekcore(52); thisweekcore(51); thisweekcore(50); thisweekcore(49); thisweekcore(48); git_thisweekdatacore += git_firstdate[6].count; git_amonthago = git_firstdate[6].date } else { thisweekcore(52); thisweekcore(51); thisweekcore(50); thisweekcore(49); thisweek2core(); git_amonthago = git_first2date[git_thisdayindex - 1].date } } var thisweek2core = () => { for (var i = git_thisdayindex - 1; i < git_first2date.length; i++) { git_thisweekdatacore += git_first2date[i].count } } var thisweekcore = (index) => { for (var item of git_data[index]) { git_thisweekdatacore += item.count } } var addlastweek = () => { for (var item of git_lastweek) { git_weekdatacore += item.count } } var addbeforeweek = () => { for (var i = git_thisdayindex; i < git_beforeweek.length; i++) { git_weekdatacore += git_beforeweek[i].count } } var addweek = (data) => { if (git_thisdayindex === 6) { git_aweekago = git_lastweek[0].date; addlastweek() } else { lastweek = data.contributions[51]; git_aweekago = lastweek[git_thisdayindex + 1].date; addlastweek(); addbeforeweek() } } fetch(git_gitapiurl).then(data => data.json()).then(data => { if (document.getElementById('git_loading')) { document.getElementById('git_loading').remove() }; git_data = data.contributions; git_total = data.total; git_first2date = git_data[48]; git_firstdate = git_data[47]; git_firstweek = data.contributions[0]; git_lastweek = data.contributions[52]; git_beforeweek = data.contributions[51]; git_thisdayindex = git_lastweek.length - 1; git_thisday = git_lastweek[git_thisdayindex].date; git_oneyearbeforeday = git_firstweek[0].date; git_monthindex = git_thisday.substring(5, 7) * 1; git_montharrbefore = git_month.splice(git_monthindex, 12 - git_monthindex); git_monthchange = git_montharrbefore.concat(git_month); addweek(data); addlastmonth(); var html = git_main_box(git_monthchange, git_data, git_user, git_color, git_total, git_thisweekdatacore, git_weekdatacore, git_oneyearbeforeday, git_thisday, git_aweekago, git_amonthago); append_div_gitcalendar(git_container, html); responsiveChart() }).catch(function (error) { console.log(error) }); window.onresize = function () { responsiveChart() }; window.onscroll = function () { if (document.querySelector('.gitmessage')) { git_tooltip_container.innerHTML = "" } }; var git_thiscolor = (color, x) => { if (x === 0) { var i = parseInt(x / 2); return color[0] } else if (x < 2) { return color[1] } else if (x < 20) { var i = parseInt(x / 2); return color[i] } else { return color[9] } }; var tooltip_html = (x, y, span1, span2) => { var html = ''; html += `<div class="gitmessage" style="top:${y}px;left: ${x}px;position: fixed;z-index:9999"> <div class="angle-wrapper" style="display:block;"> <span>${span1} </span> <span>${span2}次上传</span> </div> </div>`; return html }; var git_canvas_box = () => { var html = `<div id="gitcalendarcanvasbox"> <canvas id="gitcanvas" style="animation: none;"> </canvas> </div>`; return html }; var git_info_box = (user, color) => { var html = ''; html += `<div id="git_tooltip_container"></div> <div class="contrib-footer clearfix mt-1 mx-3 px-3 pb-1"> <div class="float-left text-gray">数据来源 <a href="https://github.com/${user}" target="blank">@${user}</a> </div> <div class="contrib-legend text-gray">Less <ul class="legend"> <li style="background-color:${color[0]}"></li> <li style="background-color:${color[2]}"></li> <li style="background-color:${color[4]}"></li> <li style="background-color:${color[6]}"></li> <li style="background-color:${color[8]}"></li> </ul>More </div> </div>`; return html }; var git_main_box = (monthchange, git_data, user, color, total, thisweekdatacore, weekdatacore, oneyearbeforeday, thisday, aweekago, amonthago) => { var html = ''; var canvasbox = git_canvas_box(); var infobox = git_info_box(user, color); html += `<div class="position-relative"> <div class="border py-2 graph-before-activity-overview"> <div class="js-gitcalendar-graph mx-md-2 mx-3 d-flex flex-column flex-items-end flex-xl-items-center overflow-hidden pt-1 is-graph-loading graph-canvas gitcalendar-graph height-full text-center"> ${canvasbox} </div> ${infobox} </div> </div>`; html += `<div style="display:flex;width:100%"> <div class="contrib-column contrib-column-first table-column"> <span class="text-muted">过去一年提交</span> <span class="contrib-number">${total}</span> <span class="text-muted">${oneyearbeforeday} - ${thisday}</span> </div> <div class="contrib-column table-column"> <span class="text-muted">最近一月提交</span> <span class="contrib-number">${thisweekdatacore}</span> <span class="text-muted">${amonthago} - ${thisday}</span> </div> <div class="contrib-column table-column"> <span class="text-muted">最近一周提交</span> <span class="contrib-number">${weekdatacore}</span> <span class="text-muted">${aweekago} - ${thisday}</span> </div> </div>`; return html }; }; var append_div_gitcalendar = (parent, text) => { if (typeof text === 'string') { var temp = document.createElement('div'); temp.innerHTML = text; var frag = document.createDocumentFragment(); while (temp.firstChild) { frag.appendChild(temp.firstChild) } parent.appendChild(frag) } else { parent.appendChild(text) } }; var git_container = document.getElementById('git_container'); var git_loading = document.getElementById('git_loading'); git_canlendar(git_user, git_gitapiurl, git_color) }}]]></content>
</entry>
<entry>
<title>标签</title>
<link href="/tags/index.html"/>
<url>/tags/index.html</url>
<content type="html"><![CDATA[]]></content>
</entry>
<entry>
<title></title>
<link href="/js/runtime/runtime.js"/>
<url>/js/runtime/runtime.js</url>
<content type="html"><![CDATA[var now = new Date();function createtime() { var grt = new Date("09/01/2022 00:00:00"); now.setTime(now.getTime() + 250); var days = (now - grt) / 1e3 / 60 / 60 / 24, dnum = Math.floor(days), hours = (now - grt) / 1e3 / 60 / 60 - 24 * dnum, hnum = Math.floor(hours); 1 == String(hnum).length && (hnum = "0" + hnum); var minutes = (now - grt) / 1e3 / 60 - 1440 * dnum - 60 * hnum, mnum = Math.floor(minutes); 1 == String(mnum).length && (mnum = "0" + mnum); var seconds = (now - grt) / 1e3 - 86400 * dnum - 3600 * hnum - 60 * mnum, snum = Math.round(seconds); 1 == String(snum).length && (snum = "0" + snum); let currentTimeHtml = ""; (currentTimeHtml = hnum < 18 && hnum >= 9 ? `<img style="width: 35px;height: 35px;" class='boardsign' src='https://gcore.jsdelivr.net/gh/Alleyway-boop/Figure_bed/image/天气icon_晴天_白天.svg' title='距离大佬也就还差一个大佬~'><span class='textTip'> <br> 本站居然运行了 ${dnum} 天</span><span id='runtime'> ${hnum} 小时 ${mnum} 分 ${snum} 秒 </span> <i class='fas fa-heartbeat' style='color:red'></i>` : `<img style="width: 35px;height: 35px;" class='boardsign' src='https://gcore.jsdelivr.net/gh/Alleyway-boop/Figure_bed/image/dark,夜间模式,黑夜模式,深色模式,暗黑模式.svg' title='夜晚了就该开开心心的玩耍,嘿嘿~'><span class='textTip'> <br> 本站居然运行了 ${dnum} 天</span><span id='runtime'> ${hnum} 小时 ${mnum} 分 ${snum} 秒 </span> <i class='fas fa-heartbeat' style='color:red'></i>`), document.getElementById("workboard") && (document.getElementById("workboard").innerHTML = currentTimeHtml);}setInterval(() => { createtime();}, 250);]]></content>
</entry>
<entry>
<title></title>
<link href="/js/runtime/runtime.min.js"/>
<url>/js/runtime/runtime.min.js</url>
<content type="html"><![CDATA[function createtime(){var e=new Date("09/01/2022 00:00:00");now.setTime(now.getTime()+250);var t=(now-e)/1e3/60/60/24,a=Math.floor(t),r=(now-e)/1e3/60/60-24*a,n=Math.floor(r);1==String(n).length&&(n="0"+n);var s=(now-e)/1e3/60-1440*a-60*n,i=Math.floor(s);1==String(i).length&&(i="0"+i);var o=(now-e)/1e3-86400*a-3600*n-60*i,l=Math.round(o);1==String(l).length&&(l="0"+l);let g="";g=n<18&&n>=9?`<img style="width: 35px;height: 35px;" class='boardsign' src='https://gcore.jsdelivr.net/gh/Alleyway-boop/Figure_bed/image/天气icon_晴天_白天.svg' title='距离大佬也就还差一个大佬~'><span class='textTip'> <br> 本站居然运行了 ${a} 天</span><span id='runtime'> ${n} 小时 ${i} 分 ${l} 秒 </span> <i class='fas fa-heartbeat' style='color:red'></i>`:`<img style="width: 35px;height: 35px;" class='boardsign' src='https://gcore.jsdelivr.net/gh/Alleyway-boop/Figure_bed/image/dark,夜间模式,黑夜模式,深色模式,暗黑模式.svg' title='夜晚了就该开开心心的玩耍,嘿嘿~'><span class='textTip'> <br> 本站居然运行了 ${a} 天</span><span id='runtime'> ${n} 小时 ${i} 分 ${l} 秒 </span> <i class='fas fa-heartbeat' style='color:red'></i>`,document.getElementById("workboard")&&(document.getElementById("workboard").innerHTML=g)}var now=new Date;setInterval(()=>{createtime()},250);]]></content>
</entry>
<entry>
<title></title>
<link href="/js/ali_font.js"/>
<url>/js/ali_font.js</url>
<content type="html"><![CDATA[!(function (c) { var l, h, a, t, i, v = '<svg><symbol id="icon-dragon_chen" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#D6B196" ></path><path d="M970.105263 512c0 224.983579-163.166316 412.186947-377.263158 450.533053v-54.460632C777.135158 870.507789 916.210526 707.206737 916.210526 512c0-222.881684-181.328842-404.210526-404.210526-404.210526S107.789474 289.118316 107.789474 512s181.328842 404.210526 404.210526 404.210526c9.081263 0 18.000842-0.754526 26.947368-1.374315v53.894736c-8.973474 0.538947-17.866105 1.374316-26.947368 1.374316-252.604632 0-458.105263-205.500632-458.105263-458.105263S259.395368 53.894737 512 53.894737s458.105263 205.500632 458.105263 458.105263z m-498.122105 265.620211L431.157895 754.526316V485.052632h-66.074948c-14.470737 110.645895-44.355368 197.066105-102.696421 260.742736l-39.747368-36.432842C306.526316 617.876211 323.368421 462.901895 323.368421 242.526316V215.578947h377.263158v53.894737H377.182316c-0.404211 58.260211-2.209684 112.128-6.359579 161.684211H700.631579v53.894737h-122.152421a481.172211 481.172211 0 0 0 76.826947 119.70021l66.479158-39.855158 27.728842 46.214737-54.460631 32.687158c29.507368 24.953263 63.757474 45.675789 102.80421 58.098526l-16.303158 51.361684c-134.224842-42.711579-222.773895-167.073684-261.551158-268.207157H485.052632v221.857684l68.985263-41.391158 27.728842 46.214737-109.783579 65.886316zM646.736842 377.263158h-215.578947v-53.894737h215.578947v53.894737z" fill="#231F20" ></path></symbol><symbol id="icon-dog_xu" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#D6B196" ></path><path d="M970.105263 512c0 224.983579-163.166316 412.186947-377.263158 450.533053v-54.460632C777.135158 870.507789 916.210526 707.206737 916.210526 512c0-222.881684-181.328842-404.210526-404.210526-404.210526S107.789474 289.118316 107.789474 512s181.328842 404.210526 404.210526 404.210526c9.081263 0 18.000842-0.754526 26.947368-1.374315v53.894736c-8.973474 0.538947-17.866105 1.374316-26.947368 1.374316-252.604632 0-458.105263-205.500632-458.105263-458.105263S259.395368 53.894737 512 53.894737s458.105263 205.500632 458.105263 458.105263z m-375.592421 150.393263c33.684211 44.544 75.210105 74.698105 124.739369 90.812632l11.425684 3.718737 10.401684-6.009264C781.204211 727.740632 808.421053 622.565053 808.421053 592.842105h-53.894737c0 22.069895-19.132632 80.869053-33.711158 103.504842-34.816-14.605474-64.538947-39.262316-89.249684-74.13221 48.316632-55.269053 92.079158-117.328842 120.535579-179.900632l-49.044211-22.285473c-23.767579 52.250947-59.742316 104.717474-100.055579 152.656842-24.010105-50.930526-41.148632-115.927579-51.658105-195.395369H700.631579v-53.894737h-155.189895A1848.050526 1848.050526 0 0 1 538.947368 161.684211h-53.894736c0 58.206316 2.155789 112.074105 6.494315 161.68421H323.368421v26.947368c0 216.549053-13.177263 263.545263-100.702316 359.046737l39.747369 36.432842c63.326316-69.093053 92.806737-118.272 105.714526-206.848H485.052632v-53.894736h-111.319579a1742.147368 1742.147368 0 0 0 3.449263-107.789474h120.158316c12.611368 98.250105 35.031579 177.475368 67.395368 238.187789-61.978947 65.536-128.053895 117.975579-173.298526 142.282106l25.519158 47.481263c47.589053-25.573053 114.095158-77.446737 177.55621-142.821053z m125.170526-411.971368l-80.842105-80.842106-38.103579 38.103579 80.842105 80.842106 38.103579-38.103579z" fill="#231F20" ></path></symbol><symbol id="icon-dog" viewBox="0 0 1024 1024"><path d="M894.814316 904.434526l83.240421-183.134315-13.824-13.204211c-0.485053-0.458105-45.648842-47.589053-47.939369-185.263158-0.134737-7.922526-0.134737-33.953684-0.134736-55.996631-30.693053 15.306105-70.090105 19.887158-106.09179 19.887157-92.752842 0-163.624421-23.983158-210.647579-71.275789a192.512 192.512 0 0 1-27.944421-36.513684H377.263158v377.263158c342.662737 0 403.105684 51.092211 494.592 128.377263 7.922526 6.682947 15.521684 13.312 22.959158 19.86021z" fill="#85C3DE" ></path><path d="M326.063158 282.947368c0 34.250105-13.231158 44.463158-29.642105 44.463158s-29.642105-10.213053-29.642106-44.463158c0-34.223158 13.231158-44.463158 29.642106-44.463157s29.642105 10.24 29.642105 44.463157zM269.473684 430.295579v311.646316L190.275368 916.210526h59.203369L323.368421 753.637053V377.263158h-26.947368c-119.403789 0-172.732632-53.382737-185.505685-107.789474h35.624421c51.092211 0 68.581053-15.764211 120.535579-62.544842 12.773053-11.506526 28.079158-25.276632 47.023158-41.741474l18.351158-15.952842-69.658947-99.139368-44.085895 30.989474 41.768421 59.472842c-11.183158 9.862737-20.884211 18.593684-29.480421 26.327579C180.736 212.156632 176.235789 215.578947 146.539789 215.578947H53.894737v26.947369c0 88.710737 66.910316 178.149053 215.578947 187.769263z m216.710737-161.414737c2.290526 71.733895 28.698947 136.326737 75.048421 182.918737C618.711579 509.628632 702.437053 538.947368 810.091789 538.947368c18.593684 0 36.190316-1.158737 52.628211-3.449263 3.745684 111.265684 33.630316 170.334316 51.496421 196.015158l-38.507789 84.722526C782.174316 742.049684 688.774737 700.631579 377.263158 700.631579v53.894737c34.277053 0 65.697684 0.512 94.639158 1.509052L374.595368 970.105263h59.203369l96.013474-211.240421c66.182737 4.338526 117.005474 11.829895 157.911578 22.016L626.229895 916.210526h59.176421l54.16421-119.134315c47.616 18.405053 79.737263 42.091789 113.125053 69.739789L805.753263 970.105263h59.203369l113.071157-248.778105-13.824-13.204211c-0.485053-0.458105-45.648842-47.589053-47.939368-185.263158C985.168842 498.553263 1024 447.811368 1024 377.263158c0-95.205053-66.506105-161.684211-161.684211-161.684211v53.894737c65.482105 0 107.789474 42.307368 107.789474 107.789474 0 89.088-87.013053 107.789474-160.013474 107.789474-92.752842 0-163.624421-23.983158-210.647578-71.27579-30.315789-30.504421-45.891368-65.832421-53.35579-98.735158 11.210105 6.952421 22.932211 13.338947 35.274105 19.186527l23.04-48.720843c-92.106105-43.654737-148.992-128.646737-219.243789-243.981473l-46.026105 28.05221c49.448421 81.246316 92.968421 148.506947 147.051789 199.302737z" fill="#231F20" ></path></symbol><symbol id="icon-goat" viewBox="0 0 1024 1024"><path d="M548.378947 646.736842a952.32 952.32 0 0 1 140.90779-161.68421H107.789474c0 107.600842 0 107.600842-63.649685 169.283368l-13.069473 12.665263L66.721684 754.526316h417.172211c20.345263-41.472 43.654737-77.446737 64.485052-107.789474z" fill="#F7C768" ></path><path d="M608.256 144.734316C555.762526 115.577263 506.098526 107.789474 485.052632 107.789474V53.894737c32.579368 0 91.270737 11.452632 149.369263 43.735579 75.290947 41.822316 130.694737 94.531368 171.385263 150.878316C755.873684 288.013474 697.101474 323.368421 646.736842 323.368421h-107.789474v-53.894737h107.789474c20.506947 0 48.424421-11.210105 80.437895-31.285895a471.04 471.04 0 0 0-118.918737-93.453473zM832.673684 342.231579c-16.384 0-29.642105 10.24-29.642105 44.463158 0 34.250105 13.231158 44.463158 29.642105 44.463158s29.642105-10.213053 29.642105-44.463158c0-34.223158-13.231158-44.463158-29.642105-44.463158zM1024 619.789474C1024 347.109053 901.066105 122.448842 686.753684 3.395368l-26.165895 47.104C914.324211 191.461053 964.688842 440.400842 969.647158 592.842105h-84.506947c-17.92-35.624421-45.352421-69.12-87.013053-101.995789l-16.788211-13.285053-16.734315 13.392842c-66.128842 52.897684-134.629053 127.083789-187.311158 209.677474H102.965895l-8.272842-20.318316C159.043368 617.013895 161.684211 603.109053 161.684211 485.052632v-53.894737h485.052631v-53.894737H161.684211c0-80.384 14.309053-110.026105 66.586947-137.916632l-25.384421-47.535158C123.365053 234.226526 107.789474 291.920842 107.789474 377.263158v107.789474c0 107.600842 0 107.600842-63.649685 169.283368l-13.069473 12.665263L110.618947 862.315789h58.206316l-43.897263-107.789473h103.477895l43.897263 107.789473h58.206316l-43.897263-107.789473h259.47621C508.981895 824.939789 485.052632 899.152842 485.052632 970.105263h53.894736c0-68.688842 27.270737-144.060632 68.958316-215.578947H687.157895c7.410526 0 13.473684 6.063158 13.473684 13.473684V862.315789h53.894737v-94.315789c0-37.160421-30.208-67.368421-67.368421-67.368421h-44.65179c40.771368-58.017684 89.438316-111.427368 138.913684-153.626947C841.512421 600.037053 862.315789 655.225263 862.315789 754.526316h53.894737c0-38.912-2.748632-74.482526-11.102315-107.789474H1024v-26.947368z" fill="#231F20" ></path></symbol><symbol id="icon-goat_wei" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#D6B196" ></path><path d="M970.105263 512c0 224.983579-163.166316 412.186947-377.263158 450.533053v-54.460632C777.135158 870.507789 916.210526 707.206737 916.210526 512c0-222.881684-181.328842-404.210526-404.210526-404.210526S107.789474 289.118316 107.789474 512s181.328842 404.210526 404.210526 404.210526c9.081263 0 18.000842-0.754526 26.947368-1.374315v53.894736c-8.973474 0.538947-17.866105 1.374316-26.947368 1.374316-252.604632 0-458.105263-205.500632-458.105263-458.105263S259.395368 53.894737 512 53.894737s458.105263 205.500632 458.105263 458.105263z m-431.157895 50.202947c52.304842 70.925474 136.973474 152.144842 232.528843 190.383158l19.994947-50.041263c-109.271579-43.708632-202.805895-152.629895-238.780632-217.49221H808.421053v-53.894737H538.947368v-53.894737h215.578948v-53.894737h-215.578948V161.684211h-53.894736v161.68421h-215.578948v53.894737h215.578948v53.894737H215.578947v53.894737h255.757474c-35.974737 64.862316-129.536 173.783579-238.807579 217.49221l20.021895 50.041263c95.528421-38.238316 180.197053-119.484632 232.501895-190.383158V808.421053h53.894736v-246.218106z" fill="#231F20" ></path></symbol><symbol id="icon-dragon" viewBox="0 0 1024 1024"><path d="M366.376421 344.441263l152.980211-152.98021c43.142737-43.142737 141.204211-9.216 270.201263 115.738947-15.225263 9.835789-25.114947 15.818105-44.13979 32.256s-38.076632 35.489684-59.418947 56.832c-4.203789 4.203789-51.173053 53.221053-78.740211 82.027789-10.805895-12.126316-22.743579-24.171789-34.654315-36.082526L493.136842 362.792421l-54.218105 54.218105-72.542316-72.569263zM862.315789 512c0 46.834526-45.352421 80.842105-107.789473 80.842105-108.948211 0-189.359158-28.806737-267.129263-56.697263C414.100211 509.871158 344.872421 485.052632 258.182737 485.052632 80.788211 485.052632 0 588.126316 0 683.897263h53.894737C73.216 659.779368 135.302737 646.736842 177.340632 646.736842c77.338947 0 223.124211 23.282526 291.893894 47.912421C547.462737 722.701474 615.989895 754.526316 734.315789 754.526316 862.315789 754.526316 916.210526 670.315789 916.210526 512h-53.894737z" fill="#FF8787" ></path><path d="M552.421053 1024c-69.766737 0-113.825684-13.958737-156.402527-27.459368-54.487579-17.273263-110.807579-35.004632-232.421052-26.516211l-3.826527-53.733053c131.718737-9.458526 195.934316 10.967579 252.52379 28.887579 42.226526 13.365895 78.686316 24.926316 140.126316 24.926316 92.752842 0 148.210526-57.936842 148.210526-113.960421 0-16.949895-5.524211-101.618526-114.634105-101.618526-64.970105 0-112.747789 23.336421-163.328 48.02021C365.325474 830.571789 300.301474 862.315789 204.288 862.315789 85.908211 862.315789 0 787.294316 0 683.897263 0 588.126316 80.788211 485.052632 258.182737 485.052632c86.689684 0 155.917474 24.818526 229.214316 51.09221 45.810526 16.410947 92.564211 33.172211 145.488842 44.166737 9.000421-7.033263 13.850947-16.276211 13.850947-26.758737 0-37.187368-37.672421-74.859789-74.13221-111.265684l-3.287579-3.287579 38.103579-38.103579 3.260631 3.287579C652.853895 446.275368 700.631579 494.026105 700.631579 553.552842c0 12.719158-2.802526 24.926316-7.976421 36.109474A594.997895 594.997895 0 0 0 754.526316 592.842105c62.437053 0 107.789474-34.007579 107.789473-80.842105 0-58.853053-52.870737-110.268632-108.840421-164.702316l-8.057263-7.841684c-19.024842 16.437895-38.076632 35.489684-59.418947 56.832l-38.103579-38.103579c74.805895-74.832842 134.898526-134.898526 268.314947-141.931789V55.619368c-63.407158 7.787789-120.993684 39.424-121.667368 39.801264l-15.818105 8.811789-14.120421-11.344842C731.701895 66.452211 709.712842 53.894737 673.684211 53.894737c-41.418105 0-74.347789 25.869474-109.190737 53.301895-26.624 20.911158-54.137263 42.549895-86.851369 53.194105L469.342316 161.684211h-69.093053l-105.525895 105.525894-38.103579-38.130526L324.015158 161.684211H161.684211V107.789474h303.104c22.231579-8.272842 43.708632-25.168842 66.398315-42.981053C569.829053 34.438737 613.618526 0 673.684211 0c48.909474 0 81.408 17.946947 110.888421 40.097684C813.702737 26.300632 877.729684 0 943.157895 0h26.947368v323.368421h-53.894737v-53.167158c-54.164211 3.098947-92.914526 15.845053-127.002947 36.675369l1.832421 1.778526C852.587789 368.505263 916.210526 430.376421 916.210526 512c0 60.928-43.708632 109.945263-107.789473 127.622737V700.631579h53.894736v-53.894737h53.894737v53.894737h53.894737v53.894737h-53.894737v53.894737h-53.894737v-53.894737h-53.894736c-29.722947 0-53.894737-24.171789-53.894737-53.894737v-53.894737c-118.325895 0-207.063579-31.797895-285.318737-59.877053C400.437895 562.229895 335.494737 538.947368 258.182737 538.947368 117.059368 538.947368 53.894737 611.732211 53.894737 683.897263 53.894737 757.221053 115.738947 808.421053 204.288 808.421053c11.910737 0 23.228632-0.538947 34.034526-1.536C248.454737 796.321684 269.473684 770.640842 269.473684 739.166316c0-33.118316-43.088842-70.979368-58.152421-81.596632l30.935579-44.139789c8.299789 5.793684 81.111579 58.664421 81.111579 125.736421 0 19.429053-4.527158 37.052632-10.994526 52.304842 30.773895-10.051368 58.314105-23.498105 86.662737-37.349053C452.877474 727.848421 508.577684 700.631579 585.997474 700.631579 702.410105 700.631579 754.526316 778.725053 754.526316 856.144842 754.526316 938.657684 678.912 1024 552.421053 1024z m-21.180632-623.104L493.136842 362.792421l137.889684-137.889684 38.103579 38.103579-137.889684 137.889684z m-126.760421-18.351158l-38.103579-38.103579 152.980211-152.98021 38.103579 38.103579-152.980211 152.98021z m282.004211-218.624c15.494737-9.754947 43.331368-31.447579 43.331368-31.447579-25.734737-27.809684-49.556211-33.333895-67.368421-29.07621-19.240421 4.608-37.753263 24.602947-37.753263 24.602947s42.253474 22.447158 61.790316 35.920842z" fill="#231F20" ></path></symbol><symbol id="icon-horse" viewBox="0 0 1024 1024"><path d="M776.003368 646.736842c16.599579-99.947789 43.439158-181.086316 83.213474-256.538947l6.817684-12.934737H269.473684c-36.756211 0-53.894737 54.945684-53.894737 92.05221 0 46.753684 6.656 77.527579 70.278737 176.074106l84.533895 128.269473L498.876632 646.736842h277.126736z" fill="#FFAF6E" ></path><path d="M1024 0v404.210526c0 33.333895 0 134.736842-92.079158 134.736842h-13.824l-78.362947-109.056c-22.743579 49.906526-40.340211 103.046737-53.490527 162.950737h115.092211C937.310316 592.842105 970.105263 625.637053 970.105263 661.638737c0 60.631579-69.389474 154.300632-77.312 164.75621l-43.008-32.471579C875.466105 759.861895 916.210526 693.813895 916.210526 661.638737c0-5.982316-8.919579-14.901895-14.901894-14.901895h-125.332211C761.128421 736.121263 754.526316 840.569263 754.526316 970.105263h-53.894737c0-283.971368 31.097263-453.605053 110.888421-605.049263l20.318316-38.534737 112.801684 156.995369c14.443789-4.419368 25.465263-20.938105 25.465263-79.306106V0h53.894737z m-161.684211 161.684211h53.894737V0h-53.894737v80.842105c-17.381053-14.955789-38.184421-26.947368-80.842105-26.947368h-134.736842v53.894737h134.736842c37.672421 0 80.842105 40.906105 80.842105 53.894737z m-107.789473 0h-215.578948v53.894736h161.684211l53.894737-53.894736zM300.894316 766.544842L400.680421 916.210526h64.754526l-95.043368-142.551579L498.876632 646.736842h167.855157a1212.631579 1212.631579 0 0 1 9.431579-53.894737h-199.383579l-175.885473 173.702737z m109.97221-184.400842l-37.861052-38.319158-132.419369 130.802526C173.729684 571.095579 161.684211 529.812211 161.684211 469.315368 161.684211 398.578526 199.464421 323.368421 269.473684 323.368421h323.368421l53.894737-53.894737H269.473684c-6.709895 0-13.258105 0.565895-19.698526 1.482105C234.927158 249.451789 204.638316 215.578947 160.633263 215.578947 65.967158 215.578947 0 349.291789 0 469.315368c0 70.170947 16.141474 136.650105 49.232842 202.671158L6.197895 723.833263l41.472 34.41179 66.128842-79.737264-8.704-16.033684C83.105684 622.133895 53.894737 558.214737 53.894737 469.315368 53.894737 368.451368 106.765474 269.473684 160.633263 269.473684c13.231158 0 25.815579 9.889684 35.43579 20.533895C142.874947 321.967158 107.789474 388.500211 107.789474 469.315368c0 78.201263 19.698526 130.937263 93.642105 243.981474l-55.296 54.622316L280.899368 970.105263h64.754527l-130.048-195.072 195.260631-192.889263z" fill="#231F20" ></path></symbol><symbol id="icon-monkey_shen" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#BBC4C9" ></path><path d="M970.105263 512c0 224.983579-163.166316 412.186947-377.263158 450.533053v-54.460632C777.135158 870.507789 916.210526 707.206737 916.210526 512c0-222.881684-181.328842-404.210526-404.210526-404.210526S107.789474 289.118316 107.789474 512s181.328842 404.210526 404.210526 404.210526c9.081263 0 18.000842-0.754526 26.947368-1.374315v53.894736c-8.973474 0.538947-17.866105 1.374316-26.947368 1.374316-252.604632 0-458.105263-205.500632-458.105263-458.105263S259.395368 53.894737 512 53.894737s458.105263 205.500632 458.105263 458.105263z m-431.157895 134.736842h161.684211v53.894737h53.894737V269.473684h-215.578948V161.684211h-53.894736v107.789473h-215.578948v431.157895h53.894737v-53.894737h161.684211v215.578947h53.894736v-215.578947z m0-161.68421h161.684211v107.789473h-161.684211v-107.789473z m-215.578947 0h161.684211v107.789473h-161.684211v-107.789473z m215.578947-161.684211h161.684211v107.789474h-161.684211v-107.789474z m-215.578947 0h161.684211v107.789474h-161.684211v-107.789474z" fill="#231F20" ></path></symbol><symbol id="icon-ox_chou" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#D6B196" ></path><path d="M970.105263 512c0 224.983579-163.166316 412.186947-377.263158 450.533053v-54.460632C777.135158 870.507789 916.210526 707.206737 916.210526 512c0-222.881684-181.328842-404.210526-404.210526-404.210526S107.789474 289.118316 107.789474 512s181.328842 404.210526 404.210526 404.210526c9.081263 0 18.000842-0.754526 26.947368-1.374315v53.894736c-8.973474 0.538947-17.866105 1.374316-26.947368 1.374316-252.604632 0-458.105263-205.500632-458.105263-458.105263S259.395368 53.894737 512 53.894737s458.105263 205.500632 458.105263 458.105263z m-161.68421 188.631579h-159.555369c13.985684-172.813474 43.115789-357.429895 70.817684-385.158737L700.631579 269.473684H323.368421v53.894737h107.169684c-1.940211 45.756632-8.192 103.962947-15.76421 161.684211H323.368421v53.894736h83.968c-9.862737 68.446316-20.264421 130.128842-25.734737 161.684211H215.578947v53.894737h592.842106v-53.894737z m-346.543158-161.684211h149.800421a3313.717895 3313.717895 0 0 0-16.842105 161.684211h-158.477474c6.036211-35.247158 16.114526-95.636211 25.519158-161.684211z m22.608842-215.578947h171.735579c-15.198316 41.121684-27.405474 100.594526-36.890948 161.684211h-150.123789c7.383579-57.505684 13.419789-115.361684 15.279158-161.684211z" fill="#231F20" ></path></symbol><symbol id="icon-monkey" viewBox="0 0 1024 1024"><path d="M757.733053 485.052632H565.894737a80.842105 80.842105 0 0 0-80.842105 80.842105v215.578947c0 40.96 43.546947 99.678316 77.446736 139.210105C596.426105 960.215579 603.055158 970.105263 603.055158 970.105263H754.526316s15.144421-18.674526 45.891368-58.071579S862.315789 809.984 862.315789 717.608421c0-89.573053-47.993263-166.346105-104.582736-232.555789z" fill="#C3D686" ></path><path d="M538.947368 1024h-53.894736c0-32.794947 25.869474-87.417263 77.446736-103.316211C528.599579 881.152 485.052632 822.433684 485.052632 781.473684c0-44.570947 36.271158-80.842105 80.842105-80.842105h80.842105v53.894737h-80.842105a26.947368 26.947368 0 0 0-26.947369 26.947368c0 19.725474 36.675368 77.473684 92.133053 134.736842h88.602947c20.210526-14.147368 88.737684-71.464421 88.737685-198.602105 0-108.382316-93.237895-202.967579-168.151579-278.986105-49.502316-50.202947-88.576-89.842526-98.735158-128.61979-11.749053-44.732632-21.584842-112.586105-26.327579-148.318315H377.263158c-45.136842 0-89.519158 8.434526-121.802105 53.894736H431.157895v53.894737c-97.28 0-107.789474 113.071158-107.789474 161.684211v53.894737h53.894737v161.68421h-53.894737v-107.789474h-26.947368c-170.253474 0-188.631579-94.234947-188.631579-134.736842 0-31.043368 35.220211-72.326737 55.727158-93.722947 2.694737-14.686316 5.847579-28.348632 9.431579-41.013895H161.684211V215.578947h31.528421C239.642947 120.993684 317.224421 107.789474 377.263158 107.789474h185.640421l2.802526 23.794526c0.134737 1.050947 12.719158 106.657684 27.944421 164.756211 6.494316 24.872421 44.624842 63.514947 84.965053 104.448C760.481684 483.813053 862.315789 587.129263 862.315789 717.608421c0 92.375579-31.124211 155.028211-61.898105 194.425263C904.919579 892.146526 970.105263 803.004632 970.105263 673.684211c0-91.405474-42.819368-154.381474-84.237474-215.255579C847.791158 402.458947 808.421053 344.576 808.421053 269.473684c0-119.349895 87.093895-161.684211 161.68421-161.68421v53.894737c-32.417684 0-107.789474 10.509474-107.789474 107.789473 0 58.502737 31.555368 104.933053 68.096 158.639158C974.282105 492.597895 1024 565.679158 1024 673.684211c0 177.286737-108.301474 296.421053-269.473684 296.421052h-161.684211c-37.672421 0-53.894737 40.906105-53.894737 53.894737zM229.214316 269.473684a384.808421 384.808421 0 0 0-14.012632 58.341053l-1.401263 8.488421-6.090105 6.117053c-22.878316 22.932211-44.813474 52.601263-46.026105 62.275368 0 56.805053 53.76 75.264 107.789473 79.386947V431.157895c0-58.691368 13.473684-119.619368 46.511158-161.684211h-86.770526zM323.368421 1024h-53.894737c0-32.794947 25.869474-87.417263 77.446737-103.316211C313.020632 881.152 269.473684 822.433684 269.473684 781.473684c0-44.570947 36.271158-80.842105 80.842105-80.842105h45.16379A188.847158 188.847158 0 0 1 565.894737 592.842105h134.736842v53.894737h-134.736842c-74.293895 0-134.736842 60.442947-134.736842 134.736842v26.516211l-53.894737 0.377263V781.473684c0-9.162105 0.646737-18.135579 1.913263-26.947368H350.315789c-14.848 0-26.947368 12.072421-26.947368 26.947368 0 19.725474 36.675368 77.473684 92.133053 134.736842H431.157895v53.894737h-53.894737c-37.672421 0-53.894737 40.906105-53.894737 53.894737z" fill="#231F20" ></path></symbol><symbol id="icon-horse_wu" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#FF8787" ></path><path d="M970.105263 512c0 224.983579-163.166316 412.186947-377.263158 450.533053v-54.460632C777.135158 870.507789 916.210526 707.206737 916.210526 512c0-222.881684-181.328842-404.210526-404.210526-404.210526S107.789474 289.118316 107.789474 512s181.328842 404.210526 404.210526 404.210526c9.081263 0 18.000842-0.754526 26.947368-1.374315v53.894736c-8.973474 0.538947-17.866105 1.374316-26.947368 1.374316-252.604632 0-458.105263-205.500632-458.105263-458.105263S259.395368 53.894737 512 53.894737s458.105263 205.500632 458.105263 458.105263z m-431.157895 26.947368h269.473685v-53.894736H538.947368v-161.684211h161.684211v-53.894737H411.001263c12.045474-33.28 20.156632-69.793684 20.156632-107.789473h-53.894737c0 121.963789-105.364211 233.391158-106.415158 234.496l38.858105 37.349052c2.883368-3.018105 43.816421-46.133895 77.392842-110.160842H485.052632v161.684211H215.578947v53.894736h269.473685v323.368421h53.894736V538.947368z" fill="#231F20" ></path></symbol><symbol id="icon-ox" viewBox="0 0 1025 1024"><path d="M540.294737 754.526316h215.578947c20.210526 0 35.112421 1.374316 53.894737 4.581052 91.863579 15.656421 145.354105 67.691789 161.684211 86.069895V916.210526h53.894736V635.580632l-7.895579-7.895579c-9.269895-9.269895-36.513684-49.232842-44.032-196.527158H540.294737a161.684211 161.684211 0 0 0-161.684211 161.68421v131.098948c43.304421 20.210526 97.28 30.585263 161.684211 30.585263z" fill="#FFAF6E" ></path><path d="M1025.347368 635.580632V916.210526h-53.894736v-71.033263c-16.330105-18.405053-69.820632-70.413474-161.684211-86.069895V916.210526h-53.894737v-161.68421h-107.789473v215.578947h-53.894737V700.631579h161.68421c100.998737 0 172.570947 38.669474 215.578948 71.868632v-115.738948c-33.684211-43.627789-51.712-137.458526-53.706106-279.498105H701.978947c-76.934737 0-127.218526-26.219789-175.804631-51.550316a1556.048842 1556.048842 0 0 0-26.839579-13.743158c-26.839579 26.004211-66.209684 44.921263-115.738948 55.511579 24.441263 22.986105 60.874105 52.116211 106.469053 72.838737l-22.312421 49.044211c-76.584421-34.816-129.589895-88.926316-150.824421-113.125053-10.644211 0.619789-21.477053 1.024-32.687158 1.024a473.734737 473.734737 0 0 1-123.365053-15.952842l-93.022315 186.314105 68.581052 53.86779C167.882105 579.557053 237.891368 538.947368 324.715789 538.947368v53.894737c-95.986526 0-170.361263 62.490947-171.088842 63.137684l-16.78821 14.282106-136.838737-107.358316 109.729684-219.809684C46.430316 314.448842 1.347368 267.371789 1.347368 199.868632 1.347368 89.815579 121.586526 53.894737 163.031579 53.894737v53.894737c-14.120421 0-107.789474 17.165474-107.789474 92.079158C55.242105 290.465684 192.188632 323.368421 284.240842 323.368421c67.907368 0 122.421895-12.988632 157.696-35.624421-42.711579-14.336-95.097263-23.120842-169.337263-18.324211l-3.503158-53.786947c95.878737-6.117053 160.148211 8.515368 211.429053 28.833684C484.244211 235.439158 486.4 225.818947 486.4 215.578947c0-48.855579-57.829053-76.288-58.394947-76.557473l22.393263-49.017263C454.063158 91.648 540.294737 131.826526 540.294737 215.578947c0 18.566737-3.422316 35.84-9.997474 51.631158 7.060211 3.584 13.985684 7.168 20.776421 10.698106C597.854316 302.322526 638.248421 323.368421 701.978947 323.368421h269.473685v26.947368c0 214.689684 35.220211 266.590316 45.999157 277.369264l7.895579 7.895579z m-729.384421 25.141894l-98.789052 118.541474 86.797473 137.835789 45.594948-28.725894-65.913263-104.690527 37.052631-44.43621C358.642526 785.192421 439.080421 808.421053 540.294737 808.421053v-53.894737c-99.893895 0-175.077053-24.549053-223.474526-72.946527l-20.857264-20.857263z" fill="#231F20" ></path></symbol><symbol id="icon-rabbit_mao" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#7DD47F" ></path><path d="M970.105263 512c0 224.983579-163.166316 412.186947-377.263158 450.533053v-54.460632C777.135158 870.507789 916.210526 707.206737 916.210526 512c0-222.881684-181.328842-404.210526-404.210526-404.210526S107.789474 289.118316 107.789474 512s181.328842 404.210526 404.210526 404.210526c9.081263 0 18.000842-0.754526 26.947368-1.374315v53.894736c-8.973474 0.538947-17.866105 1.374316-26.947368 1.374316-252.604632 0-458.105263-205.500632-458.105263-458.105263S259.395368 53.894737 512 53.894737s458.105263 205.500632 458.105263 458.105263z m-377.263158-188.631579h107.789474v323.368421c-20.48 0-39.936-11.264-40.016842-11.317895l-27.728842 46.214737c3.206737 1.940211 32.660211 18.997895 67.745684 18.997895 30.746947 0 53.894737-23.147789 53.894737-53.894737V269.473684h-215.578948v538.947369h53.894737V323.368421z m-107.789473 242.526316v-242.526316h-53.894737v196.904421l-107.789474 40.421053v-243.927579l169.094737-48.316632-14.821053-51.819789L269.473684 276.102737v304.801684l-36.405895 13.662316 18.917053 50.472421 178.741895-67.018105c-5.039158 69.928421-55.269053 106.981053-165.133474 122.933894l7.733895 53.328842C325.712842 746.657684 485.052632 723.536842 485.052632 565.894737z" fill="#231F20" ></path></symbol><symbol id="icon-rabbit" viewBox="0 0 1024 1024"><path d="M680.96 488.744421a1666.667789 1666.667789 0 0 0-54.433684-23.95621c-16.006737 12.234105-33.899789 20.264421-60.631579 20.264421h-80.842105c-36.810105 0-83.644632 30.396632-104.394106 67.772631-42.819368 77.123368-53.409684 117.813895-11.021473 201.701053C397.096421 808.879158 431.157895 876.409263 431.157895 970.105263h338.539789l68.338527-138.859789c20.129684-40.96 24.252632-73.701053 24.252631-110.349474 0.026947-57.397895-25.061053-159.717053-181.328842-232.151579z" fill="#FFBDD8" ></path><path d="M862.315789 720.896c0 36.621474-4.122947 69.389474-24.252631 110.349474L769.697684 970.105263H485.052632v-53.894737h48.370526C507.877053 880.074105 485.052632 833.509053 485.052632 781.473684c0-59.418947 24.171789-113.313684 63.218526-152.360421l38.103579 38.103579A161.091368 161.091368 0 0 0 538.947368 781.473684c0 54.784 35.381895 104.043789 63.514948 134.736842h133.712842l53.490526-108.759579c15.710316-31.851789 18.755368-55.834947 18.755369-86.554947 0-80.976842-63.434105-150.096842-178.607158-195.503158-17.542737 8.138105-38.292211 13.554526-63.919158 13.554526h-80.842105c-13.958737 0-43.924211 15.979789-57.290106 40.016843l-47.104-26.165895C401.408 515.449263 448.242526 485.052632 485.052632 485.052632h80.842105c37.268211 0 57.478737-15.440842 79.090526-36.45979C625.367579 336.195368 549.753263 269.473684 485.052632 269.473684h-107.789474a21.288421 21.288421 0 0 0-5.955369 2.021053A683.762526 683.762526 0 0 0 302.187789 194.021053c-35.84-34.223158-61.763368-58.933895-94.908631-79.440842A42.442105 42.442105 0 0 0 185.478737 107.789474a22.824421 22.824421 0 0 0-17.381053 7.194947c-10.913684 11.425684-6.063158 28.240842 1.428211 39.181474 21.989053 32.121263 47.912421 56.858947 83.752421 91.109052 20.614737 19.671579 49.259789 43.169684 77.392842 63.08379C281.007158 367.400421 215.578947 484.432842 215.578947 592.842105c0 74.482526 24.791579 124.065684 51.065264 176.586106C294.534737 825.209263 323.368421 882.903579 323.368421 970.105263h-53.894737c0-74.482526-24.791579-124.065684-51.065263-176.586105C190.517895 737.738105 161.684211 680.043789 161.684211 592.842105c0-90.866526 42.226526-197.685895 93.453473-274.485894a803.759158 803.759158 0 0 1-39.046737-34.115369C177.852632 247.754105 150.231579 221.399579 125.035789 184.616421c-24.441263-35.759158-22.797474-78.686316 4.069053-106.819368 26.300632-27.567158 70.898526-31.043368 106.522947-9.000421 37.941895 23.444211 65.562947 49.798737 103.774316 86.258526 9.970526 9.512421 33.037474 32.309895 56.93979 60.550737h68.634947c-27.621053-37.780211-60.416-72.730947-88.522105-99.543579-28.833684-27.540211-54.730105-52.116211-84.533895-74.024421L326.305684 0.296421c31.232 23.228632 57.802105 48.532211 87.309474 76.719158 53.840842 51.388632 94.450526 100.594526 121.74821 146.83621 82.836211 26.650947 150.042947 116.870737 165.025685 230.750316l1.724631 13.177263-9.404631 9.404632c-3.772632 3.772632-7.706947 7.653053-11.802948 11.587368C837.227789 561.178947 862.315789 663.498105 862.315789 720.896zM309.463579 754.526316c3.934316 8.057263 7.895579 16.087579 11.991579 24.144842C348.887579 832.970105 377.263158 889.128421 377.263158 970.105263h53.894737c0-93.696-34.061474-161.226105-61.520842-215.578947h-60.173474z m597.90821 53.894737c-3.422316 9.404632-7.814737 19.806316-13.770105 31.959579L829.790316 970.105263h60.065684l52.143158-105.957052c10.778947-21.935158 17.515789-40.016842 21.90821-55.727158h-56.535579zM514.694737 390.736842c0-34.223158-13.231158-44.463158-29.642105-44.463158s-29.642105 10.24-29.642106 44.463158c0 34.250105 13.231158 44.463158 29.642106 44.463158s29.642105-10.213053 29.642105-44.463158z" fill="#231F20" ></path></symbol><symbol id="icon-rat_zi" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#85C3DE" ></path><path d="M970.105263 512c0 224.983579-163.166316 412.186947-377.263158 450.533053v-54.460632C777.135158 870.507789 916.210526 707.206737 916.210526 512c0-222.881684-181.328842-404.210526-404.210526-404.210526S107.789474 289.118316 107.789474 512s181.328842 404.210526 404.210526 404.210526c9.081263 0 18.000842-0.754526 26.947368-1.374315v53.894736c-8.973474 0.538947-17.866105 1.374316-26.947368 1.374316-252.604632 0-458.105263-205.500632-458.105263-458.105263S259.395368 53.894737 512 53.894737s458.105263 205.500632 458.105263 458.105263z m-431.157895 188.631579v-215.578947h269.473685v-53.894737H538.947368v-39.585684c26.543158-18.081684 94.585263-65.050947 177.852632-127.488L700.631579 215.578947H323.368421v53.894737h295.316211a4221.008842 4221.008842 0 0 1-121.640421 85.369263l-11.991579 8.003369V431.157895H242.526316v53.894737h242.526316v215.578947c0 48.343579-13.850947 53.894737-134.736843 53.894737v53.894737c105.391158 0 188.631579 0 188.631579-107.789474z" fill="#231F20" ></path></symbol><symbol id="icon-rat" viewBox="0 0 1024 1024"><path d="M727.659789 431.157895c-132.581053 0-220.348632 47.454316-285.803789 154.354526-19.779368 32.309895-15.845053 76.503579-9.404632 96.579368 3.260632 10.159158 7.760842 18.647579 12.422737 25.546106C464.761263 737.010526 499.927579 754.526316 538.947368 754.526316h66.829474c1.158737 17.893053-1.967158 34.762105-15.144421 53.975579-12.692211 18.539789-37.807158 40.151579-56.32 54.810947 25.249684-0.673684 52.709053-0.997053 83.240421-0.997053C877.487158 862.315789 970.105263 711.922526 970.105263 571.176421 936.421053 512 882.364632 431.157895 727.659789 431.157895z" fill="#85C3DE" ></path><path d="M210.432 1012.897684l-43.573895-31.690105c106.954105-147.051789 185.317053-171.196632 423.828211-172.705684 21.396211-31.258947 16.249263-56.266105 9.377684-89.70779-3.557053-17.138526-7.221895-34.842947-7.221895-54.433684 0-68.958316 25.330526-104.636632 63.407158-136.973474l34.896842 41.040842c-29.453474 25.061053-44.409263 46.780632-44.409263 95.932632 0 14.093474 2.937263 28.402526 6.063158 43.546947 5.901474 28.510316 12.8 62.032842-1.131789 99.462737 166.373053-10.24 264.542316-96.902737 264.542315-236.193684C916.210526 418.330947 827.580632 323.368421 684.921263 323.368421c-83.644632 0-153.303579 29.696-174.187789 39.612632a224.875789 224.875789 0 0 1-20.533895 31.339789l-41.741474-34.115368 20.884211 17.057684-20.911158-16.976842C448.781474 359.828211 485.052632 314.287158 485.052632 262.736842c0-34.816-8.946526-60.766316-26.570106-77.069474-17.515789-16.249263-44.786526-24.602947-81.219368-24.953263V323.368421h-53.894737V109.783579l24.872421-1.913263c64.700632-4.931368 114.095158 7.895579 146.863158 38.238316C524.207158 173.056 538.947368 212.291368 538.947368 262.736842c0 11.102316-1.131789 21.908211-3.072 32.202105 37.268211-12.584421 89.842526-25.465263 149.045895-25.465263C858.165895 269.473684 970.105263 387.907368 970.105263 571.176421 970.105263 711.922526 877.487158 862.315789 617.552842 862.315789c-258.667789 0-311.942737 19.698526-407.120842 150.581895z m19.105684-256.835368c-12.045474 0-24.387368-0.565895-37.025684-1.64379l-22.096842-1.859368-2.425263-22.016C167.747368 728.144842 161.684211 672.444632 161.684211 631.026526c0-103.585684 21.450105-178.903579 53.894736-259.045052V107.789474h53.894737v274.782315l-2.021052 4.904422C235.439158 465.758316 215.578947 533.800421 215.578947 631.026526c0 22.878316 2.101895 51.442526 3.826527 70.979369 99.678316 2.802526 172.813474-35.408842 222.450526-116.493474l48.020211 24.090947c-11.237053 28.133053-11.371789 51.577263-0.377264 67.853474 9.701053 14.282105 28.645053 23.174737 49.448421 23.174737v53.894737c-39.019789 0-74.186105-17.515789-94.073263-46.888421a100.244211 100.244211 0 0 1-12.422737-25.546106c-53.221053 49.178947-121.128421 73.943579-202.913684 73.970527zM379.957895 525.473684c0-34.223158-13.231158-44.463158-29.642106-44.463158s-29.642105 10.24-29.642105 44.463158c0 34.250105 13.231158 44.463158 29.642105 44.463158s29.642105-10.213053 29.642106-44.463158z" fill="#231F20" ></path></symbol><symbol id="icon-rooster_you" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#BBC4C9" ></path><path d="M970.105263 512c0 224.983579-163.166316 412.186947-377.263158 450.533053v-54.460632C777.135158 870.507789 916.210526 707.206737 916.210526 512c0-222.881684-181.328842-404.210526-404.210526-404.210526S107.789474 289.118316 107.789474 512s181.328842 404.210526 404.210526 404.210526c9.081263 0 18.000842-0.754526 26.947368-1.374315v53.894736c-8.973474 0.538947-17.866105 1.374316-26.947368 1.374316-252.604632 0-458.105263-205.500632-458.105263-458.105263S259.395368 53.894737 512 53.894737s458.105263 205.500632 458.105263 458.105263z m-215.578947-188.631579h-161.684211v-26.947368h161.684211V242.526316H269.473684v53.894737h161.684211v26.947368h-161.684211v485.052632h53.894737v-53.894737h377.263158v53.894737h53.894737V323.368421zM323.368421 646.736842h377.263158v53.894737H323.368421v-53.894737z m0-269.473684h107.789474c0 103.316211-72.784842 107.654737-81.084632 107.789474L350.315789 538.947368c46.592 0 134.736842-33.792 134.736843-161.68421h53.894736v107.789474c0 29.722947 24.171789 53.894737 53.894737 53.894736h107.789474v53.894737H323.368421v-215.578947z m377.263158 0v107.789474h-107.789474v-107.789474h107.789474z m-215.578947-80.842105h53.894736v26.947368h-53.894736v-26.947368z" fill="#231F20" ></path></symbol><symbol id="icon-rooster" viewBox="0 0 1024 1024"><path d="M891.688421 506.421895C877.244632 455.033263 862.315789 401.893053 862.315789 323.368421V116.224l-323.368421 195.745684V323.368421c0 78.524632 14.928842 131.664842 29.372632 183.053474 12.611368 44.894316 24.522105 87.282526 24.522105 140.314947 0 101.618526-77.931789 176.693895-168.286316 203.991579l5.416422 11.587368h215.578947c24.333474 0 43.385263-0.242526 58.556631-2.128842C811.52 846.821053 916.210526 764.550737 916.210526 646.736842c0-53.032421-11.910737-95.420632-24.522105-140.314947z" fill="#FF8787" ></path><path d="M673.684211 354.357895c-16.384 0-29.642105-10.213053-29.642106-44.463158 0-34.223158 13.231158-44.463158 29.642106-44.463158s29.642105 10.24 29.642105 44.463158c0 34.250105-13.258105 44.463158-29.642105 44.463158zM540.106105 970.105263l-50.58021-107.789474h156.05221l50.607158 107.789474h59.553684l-51.60421-109.918316C811.52 846.821053 916.210526 764.550737 916.210526 646.736842c0-53.032421-11.910737-95.420632-24.522105-140.314947C877.244632 455.033263 862.315789 401.893053 862.315789 323.368421V107.789474c0-59.445895-48.343579-107.789474-107.789473-107.789474a107.924211 107.924211 0 0 0-107.789474 106.172632 100.890947 100.890947 0 0 0-24.117895-3.314527 88.710737 88.710737 0 0 0-88.602947 88.602948c0 20.668632 5.227789 39.720421 10.671158 53.921684l-99.489684 59.688421 93.749894 14.470737V377.263158c0 14.416842-5.901474 21.692632-33.360842 49.152l-11.129263 11.129263C398.228211 326.521263 324.985263 269.473684 215.740632 269.473684 96.768 269.473684 0 366.241684 0 485.214316V646.736842h53.894737v-161.522526A162.007579 162.007579 0 0 1 215.740632 323.368421c82.081684 0 140.422737 36.244211 240.64 152.252632l-38.615579 38.615579C367.804632 461.285053 323.098947 431.157895 259.584 431.157895A151.983158 151.983158 0 0 0 107.789474 582.952421V754.526316h53.894737v-171.573895A98.007579 98.007579 0 0 1 259.584 485.052632c46.322526 0 79.629474 20.911158 137.027368 86.016l18.970948 21.530947 128.080842-128.080842C572.200421 435.981474 592.842105 415.366737 592.842105 377.263158v-97.926737l23.309474-14.120421-13.662316-23.04c-0.161684-0.242526-14.578526-24.899368-14.578526-50.688 0-19.132632 15.575579-34.708211 34.70821-34.708211 5.093053 0 26.785684 3.179789 39.558737 18.647579l26.327579 46.026106 39.774316-24.090948-20.372211-49.367579C704.754526 140.449684 700.631579 117.517474 700.631579 107.789474c0-29.722947 24.171789-53.894737 53.894737-53.894737s53.894737 24.171789 53.894737 53.894737v215.578947c0 85.935158 16.680421 145.300211 31.366736 197.632C851.887158 564.008421 862.315789 601.141895 862.315789 646.736842c0 95.285895-99.408842 161.684211-188.631578 161.684211h-209.461895l-68.419369-145.704421C375.242105 618.954105 338.108632 592.842105 296.448 592.842105A80.976842 80.976842 0 0 0 215.578947 673.711158V862.315789h53.894737v-188.604631c0-14.874947 12.099368-26.974316 26.974316-26.974316 20.533895 0 38.965895 14.147368 50.553263 38.858105L480.579368 970.105263h59.526737z" fill="#231F20" ></path></symbol><symbol id="icon-snake_si" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#FF8787" ></path><path d="M970.105263 512c0 224.983579-163.166316 412.186947-377.263158 450.533053v-54.460632C777.135158 870.507789 916.210526 707.206737 916.210526 512c0-222.881684-181.328842-404.210526-404.210526-404.210526S107.789474 289.118316 107.789474 512s181.328842 404.210526 404.210526 404.210526c9.081263 0 18.000842-0.754526 26.947368-1.374315v53.894736c-8.973474 0.538947-17.866105 1.374316-26.947368 1.374316-252.604632 0-458.105263-205.500632-458.105263-458.105263S259.395368 53.894737 512 53.894737s458.105263 205.500632 458.105263 458.105263z m-242.041263 180.762947l-52.116211-13.797052C657.219368 749.864421 651.425684 754.526316 619.789474 754.526316h-242.526316V485.052632h269.473684v53.894736h53.894737V215.578947H323.368421v538.947369c0 29.722947 24.171789 53.894737 53.894737 53.894737h242.526316c77.689263 0 91.189895-51.065263 108.274526-115.658106zM377.263158 269.473684h269.473684v161.684211H377.263158v-161.684211z" fill="#231F20" ></path></symbol><symbol id="icon-tiger_yin" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#7DD47F" ></path><path d="M970.105263 512c0 224.983579-163.166316 412.186947-377.263158 450.533053v-54.460632C777.135158 870.507789 916.210526 707.206737 916.210526 512c0-222.881684-181.328842-404.210526-404.210526-404.210526S107.789474 289.118316 107.789474 512s181.328842 404.210526 404.210526 404.210526c9.081263 0 18.000842-0.754526 26.947368-1.374315v53.894736c-8.973474 0.538947-17.866105 1.374316-26.947368 1.374316-252.604632 0-458.105263-205.500632-458.105263-458.105263S259.395368 53.894737 512 53.894737s458.105263 205.500632 458.105263 458.105263z m-257.42821 299.250526l-107.789474-53.894737-24.117895 48.208843 107.789474 53.894736 24.117895-48.208842z m-269.473685-5.658947l-24.117894-48.208842-107.789474 53.894737 24.117895 48.208842 107.789473-53.894737zM700.631579 431.157895h-161.684211v-53.894737h107.789474v-53.894737H377.263158v53.894737h107.789474v53.894737h-161.684211v323.368421h53.894737v-53.894737h269.473684v53.894737h53.894737V431.157895z m-161.684211 161.68421h107.789474v53.894737h-107.789474v-53.894737z m-161.68421 0h107.789474v53.894737h-107.789474v-53.894737z m161.68421-107.789473h107.789474v53.894736h-107.789474v-53.894736z m-161.68421 0h107.789474v53.894736h-107.789474v-53.894736zM754.526316 215.578947h-223.097263l-20.803369-62.410105-51.119158 17.057684L474.624 215.578947H269.473684v107.789474h53.894737v-53.894737h377.263158v53.894737h53.894737V215.578947z" fill="#231F20" ></path></symbol><symbol id="icon-snake" viewBox="0 0 1024 1024"><path d="M107.789474 790.474105c0-72.434526 67.880421-91.513263 121.451789-91.513263 74.401684 0 153.815579 34.438737 237.891369 70.925474 50.580211 21.935158 104.609684 45.325474 162.250105 63.083789-52.412632 44.786526-118.784 74.347789-195.152842 83.078737-143.171368 16.357053-326.440421 7.006316-326.440421-125.574737zM377.263158 215.578947c-15.575579 0-30.288842 3.449263-43.654737 9.377685A250.691368 250.691368 0 0 0 323.368421 296.421053c0 115.550316 76.422737 169.391158 137.83579 212.614736 8.138105 5.712842 16.141474 11.371789 23.848421 17.057685V323.368421a107.789474 107.789474 0 0 0-107.789474-107.789474z" fill="#C3D686" ></path><path d="M671.528421 788.857263c44.328421 11.964632 89.626947 19.563789 136.892632 19.56379 89.168842 0 161.684211-60.442947 161.68421-134.736842s-72.515368-134.736842-161.68421-134.736843c-19.078737 0-37.025684 1.509053-54.218106 4.015158-0.754526-101.402947-38.211368-172.355368-79.413894-219.648L673.684211 323.368421a1749.962105 1749.962105 0 0 1-79.036632-1.751579c45.702737 35.866947 108.705684 107.870316 105.984 232.367158 0 0.431158-0.080842 0.808421-0.10779 1.239579-34.923789 10.994526-66.155789 26.731789-95.097263 45.190737a163.085474 163.085474 0 0 0-15.845052-42.388211c-21.557895-39.639579-60.065684-66.775579-97.360842-93.022316C433.098105 423.343158 377.263158 384 377.263158 296.421053c0-130.290526 108.274526-188.631579 215.578947-188.631579 64.134737 0 132.715789 12.045474 214.366316 37.807158C802.330947 180.250947 780.099368 209.381053 700.631579 214.635789V161.684211h-53.894737v53.679157c-63.272421-1.024-104.528842-5.200842-104.986947-5.254736l-5.578106 53.598315C538.408421 263.949474 592.357053 269.473684 673.684211 269.473684c125.170526 0 188.631579-48.128 188.631578-143.063579V106.981053l-18.432-6.144C747.789474 68.823579 668.025263 53.894737 592.842105 53.894737c-158.666105 0-269.473684 99.732211-269.473684 242.526316 0 115.550316 76.422737 169.391158 137.83579 212.614736 33.684211 23.713684 65.509053 46.106947 81.003789 74.698106 9.539368 17.542737 13.285053 33.414737 12.341895 47.750737 21.153684 9.108211 42.118737 17.839158 62.949052 25.977263C671.151158 620.193684 729.977263 592.842105 808.421053 592.842105c59.445895 0 107.789474 36.271158 107.789473 80.842106s-48.343579 80.842105-107.789473 80.842105c-105.472 0-203.237053-42.388211-297.768421-83.429053-94.800842-41.094737-184.346947-79.952842-281.411369-79.952842C122.718316 591.171368 53.894737 644.715789 53.894737 727.578947c0 79.063579 67.098947 136.434526 159.555368 136.434527 142.174316 0 230.426947-66.883368 306.79579-129.886316 31.420632 13.419789 62.787368 26.058105 94.450526 37.133474-47.077053 49.637053-110.969263 82.566737-186.610526 91.270736l5.066105 53.625264c93.453474-7.006316 143.144421 9.350737 195.718737 26.543157 46.457263 15.225263 94.127158 30.854737 169.822316 30.854737 19.994947 0 41.957053-1.077895 66.344421-3.557052l-5.416421-53.625263c-105.283368 10.778947-158.100211-6.548211-213.935158-24.872422-22.150737-7.275789-44.624842-14.632421-70.305684-20.345263a334.848 334.848 0 0 0 96.14821-82.297263z m-458.078316 21.261474C162.573474 810.118737 107.789474 784.276211 107.789474 727.578947c0-60.847158 62.733474-82.539789 121.451789-82.539789 77.850947 0 154.731789 30.288842 235.250526 64.943158-66.263579 52.924632-139.722105 100.136421-251.041684 100.136421z" fill="#231F20" ></path></symbol><symbol id="icon-tiger" viewBox="0 0 1024 1024"><path d="M431.157895 162.250105V134.736842c0-41.552842-39.289263-80.842105-80.842106-80.842105-28.833684 0-57.128421 4.661895-58.314105 4.850526L269.473684 62.490947v83.887158C144.788211 223.824842 89.222737 346.839579 66.991158 431.157895h266.051368c240.747789 0 415.851789 107.789474 415.85179 269.473684-14.848-25.114947-43.924211-53.894737-88.68379-53.894737-67.988211 0-121.263158 71.033263-121.263158 161.684211 0 66.802526 30.477474 119.888842 60.712421 156.16 12.638316 15.171368 36.055579 37.726316 59.014737 58.88 5.066105 0.107789 9.781895 0.538947 15.009685 0.538947 219.297684 0 350.315789-191.811368 350.315789-377.263158C1024 327.545263 679.855158 172.813474 431.157895 162.250105z" fill="#F7C768" ></path><path d="M673.684211 1024c-114.768842 0-188.820211-33.333895-254.167579-62.787368-53.625263-24.144842-99.974737-45.002105-161.28-45.002106-40.448 0-83.590737 23.255579-103.639579 45.16379l-39.747369-36.432842C142.497684 894.787368 199.168 862.315789 258.236632 862.315789c68.392421 0 119.861895 21.288421 172.921263 45.056V673.684211c0-35.166316-17.542737-64.107789-30.639158-80.815158-15.198316 9.835789-32.067368 18.890105-50.741895 26.947368l-21.342316-49.475368C469.800421 509.413053 485.052632 377.317053 485.052632 323.368421V221.642105A597.827368 597.827368 0 0 0 404.210526 215.578947h-26.947368V134.736842c0-12.099368-14.848-26.947368-26.947369-26.947368-9.377684 0-18.836211 0.592842-26.947368 1.347368V269.473684h-53.894737V211.671579c-136.030316 102.912-158.450526 266.886737-161.306947 295.882105 9.135158 9.108211 38.992842 25.061053 71.976421 38.669474l38.103579-59.365053 12.449684-1.589894C321.212632 473.653895 377.263158 392.192 377.263158 323.368421h53.894737c0 88.333474-68.796632 192.242526-180.870737 213.342316l-48.397474 75.398737-20.291368-7.437474C53.894737 557.756632 53.894737 523.317895 53.894737 512c0-50.041263 37.025684-254.733474 215.578947-365.621895V62.490947l22.528-3.745684C293.187368 58.556632 321.482105 53.894737 350.315789 53.894737c41.552842 0 80.842105 39.289263 80.842106 80.842105v27.513263c248.697263 10.563368 592.842105 165.295158 592.842105 484.486737 0 185.451789-131.018105 377.263158-350.315789 377.263158z m-13.473685-323.368421c-36.513684 0-67.368421 49.367579-67.368421 107.789474 0 85.746526 68.096 145.084632 89.465263 161.549473 91.540211-2.533053 164.378947-45.487158 213.827369-107.654737H700.631579v-53.894736h230.238316c8.919579-17.273263 16.357053-35.354947 22.285473-53.894737h-239.885473l-6.467369-17.650527C706.290526 735.582316 692.439579 700.631579 660.210526 700.631579zM485.052632 931.112421c33.926737 14.066526 70.521263 26.597053 114.607157 33.468632C569.424842 928.309895 538.947368 875.223579 538.947368 808.421053c0-90.650947 53.274947-161.684211 121.263158-161.684211 44.759579 0 73.835789 28.779789 88.68379 53.894737h217.007158c2.775579-17.866105 4.203789-35.920842 4.203789-53.894737 0-38.938947-5.658947-74.752-15.925895-107.627789l-126.706526 126.679579-38.103579-38.103579L932.001684 485.052632a367.939368 367.939368 0 0 0-57.775158-81.596632l-154.543158 154.543158-38.103579-38.103579 153.573053-153.573053a537.869474 537.869474 0 0 0-82.593684-56.751158l-140.665263 140.638316-38.103579-38.103579 128.134737-128.134737A794.731789 794.731789 0 0 0 538.947368 231.046737V323.368421c0 50.149053-11.102316 156.698947-95.932631 236.328421 18.378105 23.417263 42.037895 63.407158 42.037895 113.987369v257.42821zM215.578947 431.157895v-53.894737c39.774316 0 53.894737-29.022316 53.894737-53.894737h53.894737c0 53.571368-37.025684 107.789474-107.789474 107.789474z" fill="#231F20" ></path></symbol><symbol id="icon-boar" viewBox="0 0 1024 1024"><path d="M732.079158 377.263158c-107.789474 0-186.421895 31.393684-281.869474 126.841263L180.331789 773.982316C257.724632 807.909053 348.725895 808.421053 485.052632 808.421053h96.013473c55.834947-34.411789 133.551158-53.894737 227.354948-53.894737h121.344L970.105263 680.555789V572.631579c0-94.315789-130.236632-195.368421-238.026105-195.368421z" fill="#FFBDD8" ></path><path d="M808.421053 700.631579v53.894737c-196.446316 0-323.368421 84.641684-323.368421 215.578947h-53.894737c0-163.705263 148.075789-269.473684 377.263158-269.473684z m-323.368421 107.789474v-53.894737c-158.342737 0-245.598316 0-319.649685-49.367579L158.612211 700.631579H80.842105c-21.692632 0-26.624-14.821053-26.947368-26.947368v-82.620632c84.156632-11.183158 161.684211-74.913684 161.68421-186.853053V215.578947H161.684211v161.684211H134.736842c-66.964211 0-134.736842 37.025684-134.736842 107.789474h53.894737c0-42.630737 52.870737-53.894737 80.842105-53.894737h24.629895C147.132632 504.912842 85.153684 538.947368 26.947368 538.947368H0v134.736843c0 32.498526 21.530947 80.842105 80.842105 80.842105h61.682527c32.687158 20.506947 67.125895 33.145263 105.957052 41.013895A232.879158 232.879158 0 0 0 215.578947 916.210526h53.894737c0-41.930105 14.012632-80.303158 39.424-112.505263C358.885053 808.151579 415.959579 808.421053 485.052632 808.421053z m-72.946527-342.420211L323.368421 554.738526V431.157895h-53.894737v253.682526l180.736-180.736-38.103579-38.103579zM323.368421 161.684211h-53.894737v190.032842a769.536 769.536 0 0 1 53.894737-49.098106V161.684211z m323.368421-53.894737c-72.623158 0-146.809263 23.336421-215.578947 58.637473V107.789474h-53.894737v154.138947C458.832842 205.392842 555.331368 161.684211 646.736842 161.684211c148.587789 0 269.473684 120.885895 269.473684 269.473684v235.654737L809.579789 862.315789h61.359158L970.105263 680.555789V431.157895c0-178.310737-145.057684-323.368421-323.368421-323.368421z" fill="#231F20" ></path></symbol><symbol id="icon-boar_hai" viewBox="0 0 1024 1024"><path d="M512 512m-296.421053 0a296.421053 296.421053 0 1 0 592.842106 0 296.421053 296.421053 0 1 0-592.842106 0Z" fill="#85C3DE" ></path><path d="M309.975579 804.756211l-27.136-46.592c103.073684-60.011789 183.026526-132.473263 241.475368-219.24379H350.315789l-13.473684-50.283789c58.88-33.980632 99.435789-117.571368 118.703158-165.295158H242.526316v-53.894737h538.947368v53.894737h-268.18021c-12.395789 34.088421-42.469053 106.603789-90.435369 161.68421h134.009263a680.555789 680.555789 0 0 0 46.349474-107.708631l51.092211 17.057684c-58.421895 175.265684-171.034947 309.490526-344.333474 410.381474z m192.350316-2.937264L467.806316 760.454737c88.414316-73.728 154.516211-158.773895 202.105263-259.907369l48.801684 22.959158a797.372632 797.372632 0 0 1-82.351158 137.781895c32.741053 15.009684 83.456 44.867368 137.647158 101.591579l-38.938947 37.268211c-57.236211-59.877053-109.325474-85.557895-133.766737-95.178106a850.997895 850.997895 0 0 1-98.977684 96.848842z m48.613052-536.872421l-80.842105-53.894737 29.884632-44.840421 80.842105 53.894737-29.884632 44.840421zM512 53.894737C259.395368 53.894737 53.894737 259.395368 53.894737 512s205.500632 458.105263 458.105263 458.105263c9.081263 0 17.973895-0.835368 26.947368-1.374316v-53.894736c-8.946526 0.619789-17.866105 1.374316-26.947368 1.374315-222.881684 0-404.210526-181.328842-404.210526-404.210526S289.118316 107.789474 512 107.789474s404.210526 181.328842 404.210526 404.210526c0 195.206737-139.075368 358.507789-323.368421 396.045474v54.460631c214.096842-38.346105 377.263158-225.549474 377.263158-450.533052C970.105263 259.395368 764.604632 53.894737 512 53.894737z" fill="#231F20" ></path></symbol><symbol id="icon-bilibili1" viewBox="0 0 1129 1024"><path d="M234.909 9.656a80.468 80.468 0 0 1 68.398 0 167.374 167.374 0 0 1 41.843 30.578l160.937 140.82h115.07l160.936-140.82a168.983 168.983 0 0 1 41.843-30.578A80.468 80.468 0 0 1 930.96 76.445a80.468 80.468 0 0 1-17.703 53.914 449.818 449.818 0 0 1-35.406 32.187 232.553 232.553 0 0 1-22.531 18.508h100.585a170.593 170.593 0 0 1 118.289 53.109 171.397 171.397 0 0 1 53.914 118.288v462.693a325.897 325.897 0 0 1-4.024 70.007 178.64 178.64 0 0 1-80.468 112.656 173.007 173.007 0 0 1-92.539 25.75H212.377a341.186 341.186 0 0 1-72.421-4.024A177.835 177.835 0 0 1 28.91 939.065a172.202 172.202 0 0 1-27.36-92.539V388.662a360.498 360.498 0 0 1 0-66.789A177.03 177.03 0 0 1 162.487 178.64h105.414c-16.899-12.07-31.383-26.555-46.672-39.43a80.468 80.468 0 0 1-25.75-65.984 80.468 80.468 0 0 1 39.43-63.57M216.4 321.873a80.468 80.468 0 0 0-63.57 57.937 108.632 108.632 0 0 0 0 30.578v380.615a80.468 80.468 0 0 0 55.523 80.469 106.218 106.218 0 0 0 34.601 5.632h654.208a80.468 80.468 0 0 0 76.444-47.476 112.656 112.656 0 0 0 8.047-53.109v-354.06a135.187 135.187 0 0 0 0-38.625 80.468 80.468 0 0 0-52.304-54.719 129.554 129.554 0 0 0-49.89-7.242H254.22a268.764 268.764 0 0 0-37.82 0z m0 0" fill="#20B0E3" ></path><path d="M348.369 447.404a80.468 80.468 0 0 1 55.523 18.507 80.468 80.468 0 0 1 28.164 59.547v80.468a80.468 80.468 0 0 1-16.094 51.5 80.468 80.468 0 0 1-131.968-9.656 104.609 104.609 0 0 1-10.46-54.719v-80.468a80.468 80.468 0 0 1 70.007-67.593z m416.02 0a80.468 80.468 0 0 1 86.102 75.64v80.468a94.148 94.148 0 0 1-12.07 53.11 80.468 80.468 0 0 1-132.773 0 95.757 95.757 0 0 1-12.875-57.133V519.02a80.468 80.468 0 0 1 70.007-70.812z m0 0" fill="#20B0E3" ></path></symbol><symbol id="icon-yinle" viewBox="0 0 1024 1024"><path d="M512.2976 0a531.2 531.2 0 0 0-512 548.48V960h128V548.48a398.72 398.72 0 0 1 384-411.52 398.72 398.72 0 0 1 384 411.52V960h128V548.48A531.2 531.2 0 0 0 512.2976 0z" fill="#5c8add" ></path><path d="M64.2976 576l256 0 0 448-256 0 0-448Z" fill="#5c8add" ></path><path d="M704.2976 576l256 0 0 448-256 0 0-448Z" fill="#5c8add" ></path></symbol><symbol id="icon-icon-test-copy" viewBox="0 0 1024 1024"><path d="M512 512m-229.517241 0a229.517241 229.517241 0 1 0 459.034482 0 229.517241 229.517241 0 1 0-459.034482 0Z" fill="#5c8add" ></path><path d="M512 1024A512 512 0 1 1 1024 512 512 512 0 0 1 512 1024z m0-141.241379A370.758621 370.758621 0 1 0 141.241379 512 370.758621 370.758621 0 0 0 512 882.758621z" fill="#5c8add" ></path></symbol><symbol id="icon-V" viewBox="0 0 1024 1024"><path d="M1012.47774251 492.58192592L544.94137566 87.22962963a49.96686561 49.96686561 0 0 0-65.88275132 0L11.63784127 492.6975097c-21.03624691 18.26223633-23.3479224 49.93219048-5.08568606 70.96843739 18.03106878 21.03624691 49.93219048 23.3479224 70.96843738 5.08568607L512 191.83294532l434.71057495 376.91868784c9.47786949 8.20644797 21.26741446 12.25188008 32.82579189 12.13629629 14.10122046 0 27.97127337-5.77918871 38.02706173-17.33756613 18.14665256-20.92066314 15.95056084-52.70620106-5.08568606-70.9684374z" fill="#5c8add" ></path><path d="M109.30613051 567.59579541V896.89396825c0 42.53482892 34.90629982 77.44112875 77.44112875 77.44112875h220.76500882V666.30433862c0-25.54401411 20.92066314-46.46467725 46.46467724-46.46467724h116.16169313c25.54401411 0 46.46467725 20.92066314 46.46467725 46.46467724V974.335097h220.76500882c42.53482892 0 77.44112875-34.90629982 77.44112874-77.44112875l0.11558377-329.29817284L512 218.18604586 109.30613051 567.59579541zM848.00203175 197.49655027h-63.91782716c-12.82979894 0-23.23233862 10.40253968-23.23233863 23.23233862v24.27259259l110.49808818 95.70336508V220.72888889h-0.11558377c0-12.82979894-10.40253968-23.23233862-23.23233862-23.23233862zM905.44716754 83.18419754s-34.90629982 56.86721693-89.11508994 100.32671603c152.68616579 13.98563668 127.83565432-133.26809171 127.83565432-133.2680917-134.07717813-10.28695591-132.92134039 102.29164021-131.072 127.83565432 20.92066314-20.92066314 49.70102293-62.64640564 92.35143562-94.89427865zM798.53217637 174.61096297c-19.64924162-16.52847972-40.56990476-43.45949912-51.203612-53.97762258 0 0 32.94137566 20.57391182 56.40488184 49.3542716 2.42725926-18.37782011 6.47269135-93.3916896-93.16052205-85.3008254 0 0-13.98563668 104.71889947 87.95925221 89.92417638z" fill="#5c8add" ></path></symbol><symbol id="icon-zhifeiji" viewBox="0 0 1167 1024"><path d="M41.201759 463.52493L1110.665064 30.117647c10.32605-4.159104 21.942857 0.860504 26.101961 11.043137 1.434174 3.728852 1.864426 7.744538 1.003921 11.616807L949.033691 978.823529c-2.151261 10.89972-12.764146 17.927171-23.663865 15.632493-2.72493-0.573669-5.306443-1.721008-7.601121-3.298599L634.80624 789.79944l-163.065546 133.951821c-16.492997 13.62465-40.87395 11.186555-54.498599-5.306443-3.011765-3.728852-5.306443-7.887955-6.884034-12.477311l-102.973669-313.080112-265.178712-91.787115c-10.469468-3.585434-16.062745-15.058824-12.333893-25.528291 1.864426-5.44986 6.023529-9.895798 11.329972-12.047059z" fill="#FCFDFC" ></path><path d="M929.385512 1023.569748c-3.155182 0-6.453782-0.286835-9.752381-1.003922-6.740616-1.434174-12.907563-4.015686-18.50084-8.031372L635.953579 825.940616l-146.142297 120.040336c-13.911485 11.473389-31.408403 16.779832-49.335574 15.058824-17.927171-1.721008-34.133333-10.32605-45.463305-24.237535-5.306443-6.453782-9.322129-13.768067-11.903642-21.79944l-98.527731-299.598879-251.697479-87.19776c-12.333894-4.302521-22.229692-13.05098-27.966386-24.811204s-6.453782-24.954622-2.151261-37.288515c4.589356-13.337815 14.771989-23.9507 27.82297-29.257143L1099.908761 3.585434c24.954622-10.039216 53.351261 2.007843 63.533894 26.819048 3.585434 8.891877 4.445938 18.644258 2.581513 28.109804L977.143495 984.560224c-4.732773 23.090196-25.098039 39.009524-47.757983 39.009524z m-294.579272-233.770308l282.962465 201.357983c2.294678 1.577591 4.87619 2.72493 7.601121 3.298599 10.89972 2.151261 21.512605-4.87619 23.663865-15.632493L1137.914364 52.777591c0.860504-3.872269 0.430252-7.887955-1.003922-11.616807-4.159104-10.32605-15.919328-15.202241-26.101961-11.043137L41.201759 463.52493c-5.306443 2.151261-9.465546 6.597199-11.47339 12.047059-1.721008 5.019608-1.434174 10.469468 0.860505 15.345658 2.294678 4.87619 6.453782 8.461625 11.473389 10.182633l265.178711 91.787115L410.214644 905.967507c1.434174 4.589356 3.872269 8.748459 6.884033 12.477311 6.597199 8.031373 15.919328 12.907563 26.101961 13.911485 10.32605 1.003922 20.365266-2.007843 28.396639-8.605042l163.208963-133.951821z" fill="#4A4A4A" ></path><path d="M307.097557 592.743978l105.698599 316.091876c6.310364 18.787675 26.532213 28.970308 45.319888 22.659944 4.159104-1.434174 7.887955-3.442017 11.186555-6.166946l164.786555-133.951821-165.360224-118.892997c297.017367-287.982073 447.462185-433.980952 451.191036-437.853222 0.573669-0.573669 2.581513-3.442017 0.430252-7.027451-1.290756-1.577591-3.298599-3.298599-7.027451-2.15126-202.218487 120.327171-404.293557 242.805602-606.22521 367.291877z" fill="#CAE0EE" ></path><path d="M446.786072 934.794398c-5.736695 0-11.329972-1.290756-16.636414-3.872269-8.891877-4.445938-15.632493-12.047059-18.787675-21.512605L305.376549 592.313725l1.003921-0.573669C507.308201 467.684034 711.391114 344.058263 912.60568 224.161345l0.286835-0.143418c3.585434-1.147339 6.310364-0.286835 8.605042 2.581513l0.143417 0.143417c2.438095 4.015686 0.573669 7.457703-0.573669 8.74846-3.872269 4.015686-155.177591 150.87507-450.043698 436.705882l165.503642 119.036414-166.220728 135.09916c-3.442017 2.868347-7.457703 5.019608-11.760225 6.453782-3.728852 1.290756-7.744538 2.007843-11.760224 2.007843z m-137.967507-341.333334l105.268348 314.944538c2.868347 8.748459 9.035294 15.77591 17.210084 19.935014 8.17479 4.159104 17.496919 4.732773 26.245378 1.864426 3.872269-1.290756 7.60112-3.298599 10.756302-5.880112l163.352381-132.804482L466.434252 672.627451l1.290756-1.147339C763.308201 384.932213 915.043775 237.642577 918.772627 233.626891c0 0 2.007843-2.294678 0.286835-5.306443-1.003922-1.290756-2.438095-2.438095-5.306443-1.577591-200.784314 119.610084-404.293557 242.94902-604.934454 366.718207z" fill="#CAE0EE" ></path><path d="M460.840974 924.898599l7.457703-253.561904 165.933894 119.896918-168.658824 135.959664c-1.290756 1.003922-3.011765 0.860504-4.015686-0.430252-0.430252-0.430252-0.717087-1.147339-0.717087-1.864426z" fill="#94C3E2" ></path><path d="M463.709322 929.344538c-1.290756 0-2.438095-0.573669-3.2986-1.577591-0.573669-0.860504-1.003922-1.864426-1.003921-2.868348l7.60112-256.286834 169.519328 122.621848-1.434174 1.147339-168.658823 135.959664c-0.860504 0.717087-1.721008 1.003922-2.72493 1.003922z m6.023529-255.282913l-7.457703 250.836974c0 0.286835 0.143417 0.717087 0.286835 1.003922 0.430252 0.573669 1.434174 0.717087 2.007843 0.286835l167.22465-134.812325-162.061625-117.315406z" fill="#94C3E2" ></path></symbol><symbol id="icon-lianjie" viewBox="0 0 1079 1024"><path d="M695.355535 432.666896c-0.553495-1.10699-0.885592-2.186305-1.383737-3.265619-0.193723-0.193723-0.193723-0.359772-0.359771-0.719543-12.508983-26.318678-39.436506-43.366319-69.325226-41.013966-39.076734 3.265619-68.439634 39.021384-65.312388 79.841627 0.857917 10.516401 3.653066 20.147211 7.998 28.83708 19.78744 46.659613 11.097571 103.448181-25.377737 141.750022l-191.094085 199.950001a118.088119 118.088119 0 0 1-171.998513 0c-47.434506-49.537786-47.434506-130.098956 0-179.636742l71.234782-74.389703-0.52582-0.553494a75.911814 75.911814 0 0 0 24.326097-61.880721c-3.127246-40.820243-37.3609-71.51153-76.437634-68.24591a69.463599 69.463599 0 0 0-46.908685 23.966325l-0.166049-0.193723-72.618519 75.856464c-103.226783 107.793115-103.226783 282.36538 0 390.158495 103.171433 107.793115 270.299193 107.793115 373.498301 0l191.619904-200.1714c80.256748-83.992838 97.636485-208.307773 52.83108-310.289193z" fill="#5c8add" ></path><path d="M1002.047012 80.865592c-103.226783-107.82079-270.382217-107.82079-373.581325 0l-191.619905 200.199075c-80.284423 83.854464-97.66416 208.197074-52.997128 310.233843 0.52582 1.079315 0.857917 2.15863 1.383737 3.26562 0.166048 0.166048 0.166048 0.359772 0.332097 0.719543 12.536658 26.291004 39.46418 43.366319 69.3529 41.013966 39.076734-3.265619 68.439634-39.021384 65.312388-79.869302a78.679288 78.679288 0 0 0-7.998-28.864755c-19.78744-46.631938-11.097571-103.448181 25.377737-141.750022l191.287808-199.839302a118.088119 118.088119 0 0 1 172.026188 0c47.434506 49.537786 47.434506 130.126631 0 179.692091l-71.234782 74.417378 0.52582 0.553495a75.939489 75.939489 0 0 0-24.353772 61.88072c3.15492 40.847917 37.3609 71.51153 76.465309 68.245911a69.463599 69.463599 0 0 0 46.908685-23.938651l0.166049 0.166048 72.646194-75.856464c103.03306-107.82079 103.03306-282.642127 0-390.269194z" fill="#5c8add" ></path></symbol><symbol id="icon-liaotian" viewBox="0 0 1171 1024"><path d="M1068.71699 0.243751H102.193768C46.228437 0.243751 0.500666 45.045267 0.500666 99.74309v696.251622c0 54.697824 45.727771 99.450589 101.693102 99.450589h329.113198l120.851966 114.465677a48.652788 48.652788 0 0 0 66.641644 0l120.851966-114.465677h329.064448c55.965331 0 101.741852-44.752765 101.741852-99.450589V99.74309C1170.458842 45.045267 1124.682321 0.243751 1068.71699 0.243751z m-439.776354 596.849784h-370.989696c-27.933915 0-50.846551-22.425133-50.846551-49.774045 0-27.348912 22.912636-49.725294 50.846551-49.725294h370.989696c27.933915 0 50.846551 22.376382 50.846551 49.725294 0 27.348912-22.912636 49.774045-50.846551 49.774045z m287.18795-211.381252H254.782171a50.456549 50.456549 0 0 1-50.846551-49.725294c0-27.397662 22.912636-49.774045 50.846551-49.774045h661.346415c27.933915 0 50.846551 22.376382 50.846551 49.774045 0 27.348912-22.912636 49.725294-50.846551 49.725294z" fill="#5C8ADD" ></path></symbol><symbol id="icon-xinfeng" viewBox="0 0 1400 1024"><path d="M1301.63733163 214.78520234a207.81921797 207.81921797 0 0 1 7.02423018 52.42036465v489.73590176a205.10753818 205.10753818 0 0 1-205.05853125 205.05853125H283.05853124A205.15654424 205.15654424 0 0 1 77.99999999 756.79444971V267.20556699a201.36672685 201.36672685 0 0 1 7.02423106-52.42036465L586.24393329 562.1905874c69.44187217 51.96297217 146.36536612 49.13694404 214.1736961 0zM1103.60303056 62.0000167H283.05853124A204.50312753 204.50312753 0 0 0 106.37462518 163.41030547l489.71956641 335.75823018c62.43397646 50.77048623 127.85733457 50.31309463 194.62019765 0L1280.28693749 163.41030547A204.68281729 204.68281729 0 0 0 1103.60303056 62.0000167z m0 0" fill="#5c8add" ></path></symbol><symbol id="icon-QQ1" viewBox="0 0 1024 1024"><path d="M0 512a512 512 0 1 0 1024 0A512 512 0 1 0 0 512z" fill="#18ACFC" ></path><path d="M500.113 228.39c118.396-1.518 178.924 61.004 201 156 3.497 15.048 0.15 34.807 0 50 27.143 5.682 33.087 60.106 10 75v1h1c8.26 14.33 19.04 28.125 26 44 7.332 16.723 9.306 35.16 14 55 4.024 17.01-2.287 51.505-10 57-0.771 0.683-2.231 1.312-3 2-14.601-3.016-30.377-16.865-38-27-3.065-4.074-5.275-9.672-10-12-0.395 21.568-12.503 41.15-22 55-3.514 5.123-14.073 13.217-14 18 3.691 2.836 8.305 2.956 13 5 10.513 4.577 25.449 13.168 32 22 2.334 3.146 5.548 7.555 7 11 16.193 38.414-36.527 48.314-63 54-27.185 5.839-77.818-10.224-92-19-8.749-5.414-16.863-18.573-29-19-3.666 2.389-14.438 1.132-20 1-16.829 32.804-101.913 47.868-148 31-14.061-5.146-43.398-17.695-38-40 4.437-18.327 19.947-29.224 35-37 5.759-2.975 18.915-4.419 22-10-13.141-8.988-24.521-28.659-31-44-3.412-8.077-4.193-25.775-9-32-7.789 12.245-32.097 36.91-52 33-3.071-4.553-7.213-9.097-9-15-4.792-15.835-1.81-40.379 2-54 8.117-29.02 16.965-50.623 32-72 4.672-6.643 11.425-12.135 16-19-8.945-9.733-6.951-37.536-1-49 4.002-7.709 9.701-7.413 10-20-1.92-3.022-0.071-8.604-1-13-4.383-20.75 3.273-47.552 9-63 19.8-53.421 53.712-90.466 105-112 11.986-5.033 25.833-7.783 39-11 5.322-1.3 11.969 0.518 16-2z" fill="#FFFFFF" ></path></symbol><symbol id="icon-rss" viewBox="0 0 1024 1024"><path d="M749.61196492 908.06119793C749.61196492 560.41848146 463.58151854 274.36328126 115.93880207 274.36328126V115.93880207c434.50388795 0 792.12239584 357.61850789 792.12239586 792.12239586zM224.55858562 690.72261555a108.91682943 108.91682943 0 0 1 108.69404499 108.74355267C333.25263061 859.29616292 284.24005737 908.06119793 224.31104736 908.06119793 164.48105265 908.06119793 115.96355592 859.41993206 115.96355592 799.46616822s48.69077351-108.71879883 108.61978351-108.74355267zM641.01693522 908.06119793h-153.96879069c0-203.60020956-167.50913289-371.13409627-371.10934246-371.13409629v-153.96879068c288.03550619 0 525.07813313 237.11688843 525.07813315 525.10288697z" fill="#FFA500" ></path></symbol><symbol id="icon-youxiang" viewBox="0 0 1024 1024"><path d="M583.60666667 972h-68.08c-8.43333333 0-15.33333333-6.9-15.33333334-15.33333333V609.52c0-8.43333333 6.9-15.33333333 15.33333334-15.33333333h68.08c8.43333333 0 15.33333333 6.9 15.33333333 15.33333333V956.66666667c0 8.43333333-6.9 15.33333333-15.33333333 15.33333333z" fill="#629FF9" ></path><path d="M294.42 167c-113.62 0-205.77333333 92-205.77333333 205.31333333v336.72h411.39333333V372.31333333c0.15333333-113.31333333-92-205.31333333-205.62-205.31333333z" fill="#2166CC" ></path><path d="M519.97333333 627H216.98666667c-25.45333333 0-46-20.54666667-46-46V393.78c0-25.45333333 20.54666667-46 46-46h302.98666666c25.45333333 0 46 20.54666667 46 46V581c0 25.45333333-20.54666667 46-46 46z" fill="#D2E4FF" ></path><path d="M565.97333333 397a49.22 49.22 0 0 0-49.37333333-49.22H220.36c-27.29333333 0-49.37333333 22.08-49.37333333 49.22v10.27333333l179.4 94.60666667c11.34666667 5.98 24.84 5.98 36.18666666 0l179.4-94.60666667v-10.27333333z" fill="#FFFFFF" ></path><path d="M730.5 167h-427.8v0.46c109.78666667 4.29333333 197.49333333 94.3 197.49333333 205.00666667v336.72h411.39333334c27.29333333 0 49.37333333-22.08 49.37333333-49.22V397c0-126.96-103.19333333-230-230.46-230z" fill="#4E8DF6" ></path><path d="M845.80666667 52H681.12666667c-9.04666667 0-16.40666667 7.36-16.40666667 16.40666667v336.72a24.67133333 24.67133333 0 1 0 49.37333333 0V134.18666667h131.71333334c9.04666667 0 16.40666667-7.36 16.40666666-16.40666667V68.40666667c0-9.04666667-7.36-16.40666667-16.40666666-16.40666667z" fill="#2166CC" ></path><path d="M896.25333333 659.81333333h-35.11333333c-8.43333333 0-15.33333333-6.9-15.33333333-15.33333333v-35.11333333c0-8.43333333 6.9-15.33333333 15.33333333-15.33333334h35.11333333c8.43333333 0 15.33333333 6.9 15.33333334 15.33333334v35.11333333c0 8.58666667-6.9 15.33333333-15.33333334 15.33333333z" fill="#FFFFFF" ></path><path d="M88.8 709.18666667l-24.22666667 131.40666666c-9.66 54.43333333 26.83333333 98.59333333 81.26666667 98.59333334h213.9c54.58666667 0 106.56666667-44.16 116.22666667-98.59333334l23.15333333-131.40666666H88.8z" fill="#2974CE" ></path></symbol><symbol id="icon-gitHub" viewBox="0 0 1049 1024"><path d="M523.6581816 52C262.83923907 52 52 262.8401375 52 523.6581816c0 208.49703047 135.09433812 384.97758117 322.50789391 447.44906532 23.42658172 4.68531653 32.01647887-10.15136894 32.01647796-22.64584583 0-10.93210574-0.78163433-48.41463703-0.78163433-87.45953855-131.18885996 28.11189824-158.5200223-56.22379738-158.52002231-56.22379739-21.08437312-54.66232469-52.3201152-68.71827336-52.3201152-68.71827335-42.94858371-28.89353348 3.12384382-28.89353348 3.12384384-28.89353348 47.63479867 3.12384382 72.62285398 48.41643391 72.62285398 48.4164339 42.16784782 71.84121875 110.10538527 51.53758242 137.43654672 39.04400399 3.90457972-30.45500618 16.3990566-51.5393793 29.67427028-63.25222094-104.64023039-10.93300418-214.74561566-51.53848086-214.74561657-232.70524742 0-51.53848086 18.74126609-93.70632867 48.4164339-126.50444187-4.68621496-11.71284164-21.08527156-60.12837711 4.6844181-124.94207075 0 0 39.82563922-12.49447688 129.62738726 48.41463704 37.48253129-10.15136894 78.08980484-15.61742227 117.91454562-15.61742137s80.43201433 5.46605242 117.91454473 15.61742137c89.80264648-60.90911391 129.62828571-48.41463703 129.62828571-48.41463704 25.76879122 64.81369363 9.37063305 113.22922911 4.68531651 124.94207075 30.45410773 32.79721477 48.41463703 74.96506258 48.41463703 126.50444187 0 181.16676656-110.10538527 220.99150644-215.52545401 232.70524742 17.1797934 14.83668547 32.01647887 42.94858371 32.01647886 87.45953946 0 63.25222094-0.78163433 114.009965-0.78163523 129.62738636 0 12.49447688 8.59079468 27.33116234 32.01737731 22.64584583 187.41265734-62.4705866 322.50699547-238.95203574 322.50699546-447.44996375C995.31636231 262.8401375 783.69369203 52 523.6581816 52z" fill="#663399" ></path><path d="M230.82365863 729.03136735c-0.7807359 2.34310703-4.68531653 3.12384382-7.80916035 1.56237113s-5.46605242-4.68531653-3.90368129-7.02842356c0.7807359-2.34220859 4.68531653-3.12384382 7.80826192-1.56147269s4.68531653 4.68531653 3.90457972 7.02752512z m18.7412661 21.08437312c-2.34220859 2.34220859-7.02752512 0.78163433-9.37063305-2.34310703-3.12294539-3.12294539-3.90457972-7.80826192-1.5614727-10.15136894 2.34220859-2.34220859 6.24678922-0.7807359 9.37063305 2.34310702 3.12384382 3.90457972 3.90457972 8.58899782 1.5614727 10.15136895zM268.30618992 777.44690281c-3.12294539 2.34220859-7.80826192 0-10.15136895-3.90457972-3.12384382-3.90457972-3.12384382-9.37063305 0-10.93210574 3.12384382-2.34310703 7.80916035 0 10.15226739 3.90457972 3.12294539 3.90368129 3.12294539 8.58899782 0 10.93210574z m25.76968965 26.55042555c-2.34220859 3.12294539-7.80916035 2.34220859-12.49447688-1.56237113-3.90457972-3.90368129-5.46605242-9.37063305-2.34220859-11.71284164 2.34220859-3.12384382 7.80826192-2.34310703 12.49447687 1.56147269 3.90368129 3.12384382 4.68531653 8.58989625 2.3422086 11.71374008z m35.1403227 14.83668637c-0.78163433 3.90457972-6.24768766 5.46605242-11.71374008 3.90457972-5.46605242-1.5614727-8.58899782-6.24768766-7.80916036-9.37063305 0.78163433-3.90457972 6.24768766-5.46605242 11.71374009-3.90457972 5.46605242 1.5614727 8.58899782 5.46605242 7.80916035 9.37063305z m38.26416562 3.12384382c0 3.90457972-4.68621496 7.02752512-10.15226738 7.02752512-5.46605242 0-10.15226738-3.12294539-10.15226739-7.02752512s4.68621496-7.02842356 10.15226739-7.02842445c5.46605242 0 10.15226738 3.12384382 10.15226738 7.02842445z m35.92016106-6.24768766c0.78163433 3.90457972-3.12384382 7.80916035-8.58899872 8.58989625-5.46695086 0.78163433-10.15226738-1.5614727-10.93390172-5.46605241-0.77983747-3.90457972 3.12384382-7.80916035 8.5907947-8.58899872 5.46605242-0.78163433 10.15136894 1.56057426 10.93210574 5.46515488z m0 0" fill="#663399" ></path></symbol><symbol id="icon-bilibili" viewBox="0 0 1024 1024"><path d="M832.61667555 181.33447111h-164.32545185l74.45617778-74.45617778c12.84020148-12.84020148 12.84020148-30.8140563 0-43.65425778-12.84020148-12.84020148-30.8140563-12.84020148-43.65425778 0L573.2882963 189.04101925H450.04420741L324.2272237 63.23617185c-10.26730667-12.84020148-25.68040297-15.40096-41.08136295-7.70654815-2.57289482 0-2.57289482 2.57289482-5.13365334 5.13365333-12.84020148 12.84020148-12.84020148 30.8140563 0 43.65425779l77.02907259 77.02907259h-164.32545185c-89.86927408 0-164.32545185 74.45617778-164.32545185 164.32545184v408.24073483c0 87.29637925 74.45617778 161.75255703 164.32545185 161.75255703h25.68040296c0 30.8140563 25.68040297 53.92156445 53.92156444 53.92156444s53.92156445-25.68040297 53.92156445-53.92156444H704.23893333c2.57289482 30.8140563 28.24116148 53.92156445 59.05521778 51.34866964 28.24116148-2.57289482 48.78791111-23.10750815 51.34866964-51.34866964h20.53461333c89.86927408 0 164.32545185-74.45617778 164.32545184-164.32545186V343.09916445c-2.56075852-89.86927408-77.02907259-161.76469333-166.88621037-161.76469334z m-5.13365333 634.19429926H200.99527111c-33.37481482 0-59.05521778-28.24116148-61.61597629-61.61597629l-2.57289482-415.94728297c0-33.37481482 28.24116148-61.6159763 61.6159763-61.61597629h626.48775111c33.37481482 0 59.05521778 28.24116148 61.61597629 61.61597629l2.57289482 415.94728297c-2.57289482 35.93557333-28.24116148 61.6159763-61.6159763 61.61597629z" fill="#ff7299" ></path><path d="M403.82919111 417.55534222l15.40096 77.0290726-205.40681481 38.50846815-15.40096-77.0290726 205.40681481-38.50846815z m197.70026667 77.0290726l15.40096-77.0290726 205.40681481 38.50846815-15.40096 77.0290726-205.40681481-38.50846815z m41.08136297 161.75255703c0 2.57289482 0 7.70654815-2.57289483 10.26730667-12.84020148 28.24116148-41.08136297 46.2150163-74.45617777 48.78791111-20.53461333 0-41.08136297-10.26730667-53.92156445-25.68040296-15.40096 15.40096-33.37481482 25.68040297-53.92156445 25.68040296-30.8140563-2.57289482-59.05521778-20.53461333-74.45617777-48.78791111 0-2.57289482-2.57289482-5.13365333-2.57289481-10.26730667 0-10.26730667 7.70654815-17.97385482 17.97385481-20.53461333h2.57289482c7.70654815 0 12.84020148 2.57289482 15.40096 10.26730666 0 0 20.53461333 28.24116148 38.50846815 28.24116149 35.94770963 0 35.94770963-30.8140563 56.48232296-53.92156445 23.10750815 25.68040297 23.10750815 53.92156445 56.48232296 53.92156445 23.10750815 0 38.50846815-28.24116148 38.50846815-28.24116149 2.57289482-5.13365333 10.26730667-10.26730667 15.40096-10.26730666 10.26730667-2.57289482 17.97385482 5.13365333 20.53461333 15.40096v5.13365333h0.0364089z" fill="#ff7299" ></path></symbol></svg>', o = (o = document.getElementsByTagName("script"))[ o.length - 1 ].getAttribute("data-injectcss"), p = function (c, l) { l.parentNode.insertBefore(c, l); }; if (o && !c.__iconfont__svg__cssinject__) { c.__iconfont__svg__cssinject__ = !0; try { document.write( "<style>.svgfont {display: inline-block;width: 1em;height: 1em;fill: currentColor;vertical-align: -0.1em;font-size:16px;}</style>" ); } catch (c) { console && console.log(c); } } function d() { i || ((i = !0), a()); } function m() { try { t.documentElement.doScroll("left"); } catch (c) { return void setTimeout(m, 50); } d(); } (l = function () { var c, l = document.createElement("div"); (l.innerHTML = v), (v = null), (l = l.getElementsByTagName("svg")[0]) && (l.setAttribute("aria-hidden", "true"), (l.style.position = "absolute"), (l.style.width = 0), (l.style.height = 0), (l.style.overflow = "hidden"), (l = l), (c = document.body).firstChild ? p(l, c.firstChild) : c.appendChild(l)); }), document.addEventListener ? ~["complete", "loaded", "interactive"].indexOf(document.readyState) ? setTimeout(l, 0) : ((h = function () { document.removeEventListener("DOMContentLoaded", h, !1), l(); }), document.addEventListener("DOMContentLoaded", h, !1)) : document.attachEvent && ((a = l), (t = c.document), (i = !1), m(), (t.onreadystatechange = function () { "complete" == t.readyState && ((t.onreadystatechange = null), d()); }));})(window);]]></content>
</entry>
</search>