-
Notifications
You must be signed in to change notification settings - Fork 584
/
index.html
3434 lines (3348 loc) · 313 KB
/
index.html
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
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<meta http-equiv="Content-Style-Type" content="text/css" />
<meta name="generator" content="pandoc" />
<title></title>
<style type="text/css">code{white-space: pre;}</style>
<style type="text/css">
div.sourceCode { overflow-x: auto; }
table.sourceCode, tr.sourceCode, td.lineNumbers, td.sourceCode {
margin: 0; padding: 0; vertical-align: baseline; border: none; }
table.sourceCode { width: 100%; line-height: 100%; }
td.lineNumbers { text-align: right; padding-right: 4px; padding-left: 4px; color: #aaaaaa; border-right: 1px solid #aaaaaa; }
td.sourceCode { padding-left: 5px; }
code > span.kw { color: #007020; font-weight: bold; } /* Keyword */
code > span.dt { color: #902000; } /* DataType */
code > span.dv { color: #40a070; } /* DecVal */
code > span.bn { color: #40a070; } /* BaseN */
code > span.fl { color: #40a070; } /* Float */
code > span.ch { color: #4070a0; } /* Char */
code > span.st { color: #4070a0; } /* String */
code > span.co { color: #60a0b0; font-style: italic; } /* Comment */
code > span.ot { color: #007020; } /* Other */
code > span.al { color: #ff0000; font-weight: bold; } /* Alert */
code > span.fu { color: #06287e; } /* Function */
code > span.er { color: #ff0000; font-weight: bold; } /* Error */
code > span.wa { color: #60a0b0; font-weight: bold; font-style: italic; } /* Warning */
code > span.cn { color: #880000; } /* Constant */
code > span.sc { color: #4070a0; } /* SpecialChar */
code > span.vs { color: #4070a0; } /* VerbatimString */
code > span.ss { color: #bb6688; } /* SpecialString */
code > span.im { } /* Import */
code > span.va { color: #19177c; } /* Variable */
code > span.cf { color: #007020; font-weight: bold; } /* ControlFlow */
code > span.op { color: #666666; } /* Operator */
code > span.bu { } /* BuiltIn */
code > span.ex { } /* Extension */
code > span.pp { color: #bc7a00; } /* Preprocessor */
code > span.at { color: #7d9029; } /* Attribute */
code > span.do { color: #ba2121; font-style: italic; } /* Documentation */
code > span.an { color: #60a0b0; font-weight: bold; font-style: italic; } /* Annotation */
code > span.cv { color: #60a0b0; font-weight: bold; font-style: italic; } /* CommentVar */
code > span.in { color: #60a0b0; font-weight: bold; font-style: italic; } /* Information */
</style>
<link rel="stylesheet" href="css/vendor.css" type="text/css" />
</head>
<body>
<html xmlns="http://www.w3.org/1999/xhtml" xmlns:wb="http://open.weibo.com/wb" >
<head>
<script src="http://tjs.sjs.sinajs.cn/open/api/js/wb.js" type="text/javascript" charset="utf-8"></script>
<title>一步步搭建物联网系统(教你设计物联网系统)</title>
<meta name="keywords" content="设计物联网系统,物联网系统设计">
<meta name="description" content="一份关于如何设计物联网系统的文档">
<link rel="stylesheet" href="css/vendor.css" />
</head>
<body class="container inner wrap">
<wb:follow-button uid="1533917471" type="red_4" width="100%" height="64" ></wb:follow-button>
<table>
<tr>
<td>
<iframe src="http://ghbtns.com/github-btn.html?user=phodal&repo=designiot&type=watch&count=true&size=large" height="30" width="170" frameborder="0" scrolling="0" style="width:170px; height: 30px;" allowTransparency="true"></iframe>
</td>
<td>
<iframe src="http://ghbtns.com/github-btn.html?user=phodal&repo=designiot&type=fork&count=true&size=large" height="30" width="170" frameborder="0" scrolling="0" style="width:170px; height: 30px;" allowTransparency="true"></iframe>
</td>
<td>
<iframe src="http://ghbtns.com/github-btn.html?user=phodal&type=follow&count=true&size=large" height="30" width="240" frameborder="0" scrolling="0" style="width:240px; height: 30px;" allowTransparency="true"></iframe>
</td>
</tr>
</table>
<h2>纸质版《自己动手设计物联网》现已出版</h2>
<p><a href="./designiot.jpg" target="_blank"><img src="./designiot.jpg" alt="Designiot" style="max-width:100%;"></a></p>
<p>立即购买:<a href="https://www.amazon.cn/dp/B01IBZWTWW/ref=wl_it_dp_o_pC_nS_ttl?_encoding=UTF8&colid=BDXF90QZX6WX&coliid=I19EB97K0GNLW8">亚马逊</a>、<a href="http://search.jd.com/Search?keyword=%E8%87%AA%E5%B7%B1%E5%8A%A8%E6%89%8B%E8%AE%BE%E8%AE%A1%E7%89%A9%E8%81%94%E7%BD%91&enc=utf-8&wq=%E8%87%AA%E5%B7%B1%E5%8A%A8%E6%89%8B%E8%AE%BE%E8%AE%A1%E7%89%A9%E8%81%94%E7%BD%91&pvid=k24y6hri.l4xi28">京东</a></p><a href="http://product.dangdang.com/24000878.html">当当</a>
<h1>一步步搭建物联网系统(教你设计物联网系统)</h1>
源自毕业论文:<a href="http://ebook.designiot.cn/iot.html" title="基于REST服务的最小物联网系统设计">基于REST服务的最小物联网系统设计</a>
<script>
(function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){
(i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),
m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)
})(window,document,'script','//www.google-analytics.com/analytics.js','ga');
ga('create', 'UA-54524083-1', 'auto');
ga('send', 'pageview');
</script>
</body>
</html>
<div id="TOC">
<ul>
<li><a href="#前言"><span class="toc-section-number">1</span> 前言</a><ul>
<li><a href="#目标读者"><span class="toc-section-number">1.1</span> 目标读者</a></li>
<li><a href="#不适合人群"><span class="toc-section-number">1.2</span> 不适合人群</a></li>
<li><a href="#介绍"><span class="toc-section-number">1.3</span> 介绍</a><ul>
<li><a href="#为什么没有c"><span class="toc-section-number">1.3.1</span> 为什么没有C ?</a></li>
<li><a href="#为什么不是java"><span class="toc-section-number">1.3.2</span> 为什么不是JAVA ?</a></li>
</ul></li>
<li><a href="#如何阅读"><span class="toc-section-number">1.4</span> 如何阅读</a></li>
</ul></li>
<li><a href="#无处不在的html"><span class="toc-section-number">2</span> 无处不在的HTML</a><ul>
<li><a href="#html的helloworld"><span class="toc-section-number">2.1</span> html的hello,world</a><ul>
<li><a href="#调试helloworld"><span class="toc-section-number">2.1.1</span> 调试hello,world</a></li>
<li><a href="#说说helloworld"><span class="toc-section-number">2.1.2</span> 说说hello,world</a></li>
<li><a href="#想用中文"><span class="toc-section-number">2.1.3</span> 想用中文?</a></li>
</ul></li>
<li><a href="#其他html标记"><span class="toc-section-number">2.2</span> 其他html标记</a><ul>
<li><a href="#美妙之处"><span class="toc-section-number">2.2.1</span> 美妙之处</a></li>
<li><a href="#更多"><span class="toc-section-number">2.2.2</span> 更多</a></li>
</ul></li>
</ul></li>
<li><a href="#无处不在的javascript"><span class="toc-section-number">3</span> 无处不在的Javascript</a><ul>
<li><a href="#javascript的helloworld"><span class="toc-section-number">3.1</span> Javascript的Hello,world</a></li>
<li><a href="#更js一点"><span class="toc-section-number">3.2</span> 更js一点</a><ul>
<li><a href="#从数学出发"><span class="toc-section-number">3.2.1</span> 从数学出发</a></li>
</ul></li>
<li><a href="#设计和编程"><span class="toc-section-number">3.3</span> 设计和编程</a><ul>
<li><a href="#函数"><span class="toc-section-number">3.3.1</span> 函数</a></li>
<li><a href="#重新设计"><span class="toc-section-number">3.3.2</span> 重新设计</a></li>
<li><a href="#object和函数"><span class="toc-section-number">3.3.3</span> object和函数</a></li>
<li><a href="#面向对象"><span class="toc-section-number">3.3.4</span> 面向对象</a></li>
</ul></li>
<li><a href="#其他"><span class="toc-section-number">3.4</span> 其他</a></li>
<li><a href="#美妙之处-1"><span class="toc-section-number">3.5</span> 美妙之处</a></li>
</ul></li>
<li><a href="#无处不在的css"><span class="toc-section-number">4</span> 无处不在的CSS</a><ul>
<li><a href="#css"><span class="toc-section-number">4.1</span> CSS</a></li>
<li><a href="#关于css"><span class="toc-section-number">4.2</span> 关于CSS</a></li>
<li><a href="#代码结构"><span class="toc-section-number">4.3</span> 代码结构</a></li>
<li><a href="#样式与目标"><span class="toc-section-number">4.4</span> 样式与目标</a><ul>
<li><a href="#选择器"><span class="toc-section-number">4.4.1</span> 选择器</a></li>
</ul></li>
<li><a href="#更有趣的css"><span class="toc-section-number">4.5</span> 更有趣的CSS</a></li>
</ul></li>
<li><a href="#无处不在的三剑客"><span class="toc-section-number">5</span> 无处不在的三剑客</a><ul>
<li><a href="#hellogeek"><span class="toc-section-number">5.1</span> Hello,Geek</a></li>
<li><a href="#从源码学习"><span class="toc-section-number">5.2</span> 从源码学习</a></li>
<li><a href="#浏览器渲染过程"><span class="toc-section-number">5.3</span> 浏览器渲染过程</a><ul>
<li><a href="#html"><span class="toc-section-number">5.3.1</span> HTML</a></li>
</ul></li>
<li><a href="#dom树形结构图"><span class="toc-section-number">5.4</span> DOM树形结构图</a><ul>
<li><a href="#javascript"><span class="toc-section-number">5.4.1</span> javascript</a></li>
<li><a href="#css-1"><span class="toc-section-number">5.4.2</span> CSS</a></li>
</ul></li>
<li><a href="#css盒模型图"><span class="toc-section-number">5.5</span> CSS盒模型图</a></li>
<li><a href="#笔记"><span class="toc-section-number">5.6</span> 笔记</a></li>
</ul></li>
<li><a href="#gnulinux-强大且free"><span class="toc-section-number">6</span> GNU/Linux 强大且Free</a><ul>
<li><a href="#什么是linux"><span class="toc-section-number">6.1</span> 什么是Linux</a></li>
<li><a href="#操作系统"><span class="toc-section-number">6.2</span> 操作系统</a><ul>
<li><a href="#linux架构图"><span class="toc-section-number">6.2.1</span> Linux架构图</a></li>
<li><a href="#shell"><span class="toc-section-number">6.2.2</span> Shell</a></li>
<li><a href="#gcc"><span class="toc-section-number">6.2.3</span> GCC</a></li>
<li><a href="#启动引导程序"><span class="toc-section-number">6.2.4</span> 启动引导程序</a></li>
</ul></li>
<li><a href="#从编译开始"><span class="toc-section-number">6.3</span> 从编译开始</a><ul>
<li><a href="#开始之前"><span class="toc-section-number">6.3.1</span> 开始之前</a></li>
<li><a href="#编译nginx"><span class="toc-section-number">6.3.2</span> 编译Nginx</a></li>
<li><a href="#其他-1"><span class="toc-section-number">6.3.3</span> 其他</a></li>
</ul></li>
<li><a href="#包管理"><span class="toc-section-number">6.4</span> 包管理</a></li>
<li><a href="#ubuntu-lnmp"><span class="toc-section-number">6.5</span> Ubuntu LNMP</a><ul>
<li><a href="#update软件包列表"><span class="toc-section-number">6.5.1</span> Update软件包列表</a></li>
<li><a href="#安装mysql"><span class="toc-section-number">6.5.2</span> 安装MySQL</a></li>
<li><a href="#安装nginx"><span class="toc-section-number">6.5.3</span> 安装Nginx</a></li>
<li><a href="#安装php"><span class="toc-section-number">6.5.4</span> 安装PHP</a></li>
</ul></li>
</ul></li>
<li><a href="#arduino-极客的玩具"><span class="toc-section-number">7</span> Arduino 极客的玩具</a><ul>
<li><a href="#极客的玩具"><span class="toc-section-number">7.1</span> 极客的玩具</a></li>
<li><a href="#硬件熟悉"><span class="toc-section-number">7.2</span> 硬件熟悉</a></li>
<li><a href="#开发环境"><span class="toc-section-number">7.3</span> 开发环境</a></li>
<li><a href="#点亮一个led"><span class="toc-section-number">7.4</span> 点亮一个LED</a></li>
<li><a href="#串口通信"><span class="toc-section-number">7.5</span> 串口通信</a><ul>
<li><a href="#关于arduino-setup"><span class="toc-section-number">7.5.1</span> 关于Arduino Setup()</a></li>
</ul></li>
</ul></li>
<li><a href="#python-代码如散文"><span class="toc-section-number">8</span> Python 代码如散文</a><ul>
<li><a href="#代码与散文"><span class="toc-section-number">8.1</span> 代码与散文</a><ul>
<li><a href="#开始之前-1"><span class="toc-section-number">8.1.1</span> 开始之前</a></li>
<li><a href="#python的helloworld"><span class="toc-section-number">8.1.2</span> Python的Hello,World</a></li>
<li><a href="#我们想要的helloworld"><span class="toc-section-number">8.1.3</span> 我们想要的Hello,World</a></li>
</ul></li>
<li><a href="#算法"><span class="toc-section-number">8.2</span> 算法</a></li>
<li><a href="#实用主义哲学"><span class="toc-section-number">8.3</span> 实用主义哲学</a></li>
<li><a href="#包管理-1"><span class="toc-section-number">8.4</span> 包管理</a><ul>
<li><a href="#python-requests"><span class="toc-section-number">8.4.1</span> python requests</a></li>
</ul></li>
</ul></li>
<li><a href="#raspberry-pi"><span class="toc-section-number">9</span> Raspberry Pi</a><ul>
<li><a href="#geek的盛宴"><span class="toc-section-number">9.1</span> Geek的盛宴</a></li>
<li><a href="#raspberry-pi-初始化"><span class="toc-section-number">9.2</span> Raspberry Pi 初始化</a></li>
<li><a href="#raspberry-pi-gpio"><span class="toc-section-number">9.3</span> Raspberry Pi GPIO</a></li>
</ul></li>
<li><a href="#server-一切皆为服务"><span class="toc-section-number">10</span> Server 一切皆为服务</a><ul>
<li><a href="#服务器"><span class="toc-section-number">10.1</span> 服务器</a></li>
<li><a href="#web服务器"><span class="toc-section-number">10.2</span> Web服务器</a></li>
<li><a href="#lnmp"><span class="toc-section-number">10.3</span> LNMP</a></li>
</ul></li>
<li><a href="#web服务"><span class="toc-section-number">11</span> Web服务</a><ul>
<li><a href="#soap-vs-restful"><span class="toc-section-number">11.1</span> SOAP VS RESTful</a></li>
</ul></li>
<li><a href="#http-熟悉陌生"><span class="toc-section-number">12</span> HTTP 熟悉&陌生</a><ul>
<li><a href="#你所没有深入的http"><span class="toc-section-number">12.1</span> 你所没有深入的HTTP</a><ul>
<li><a href="#打开网页时发生了什么"><span class="toc-section-number">12.1.1</span> 打开网页时发生了什么</a></li>
<li><a href="#url组成"><span class="toc-section-number">12.1.2</span> URL组成</a></li>
</ul></li>
<li><a href="#一次http-get请求"><span class="toc-section-number">12.2</span> 一次HTTP GET请求</a><ul>
<li><a href="#http响应"><span class="toc-section-number">12.2.1</span> HTTP响应</a></li>
</ul></li>
</ul></li>
<li><a href="#设计restful-api"><span class="toc-section-number">13</span> 设计RESTful API</a><ul>
<li><a href="#资源"><span class="toc-section-number">13.0.1</span> 资源</a></li>
<li><a href="#设计restful-api-1"><span class="toc-section-number">13.1</span> 设计RESTful API</a></li>
<li><a href="#rest关键目标"><span class="toc-section-number">13.2</span> REST关键目标</a></li>
<li><a href="#判断是否是-restful的约束条件"><span class="toc-section-number">13.3</span> 判断是否是 RESTful的约束条件</a></li>
<li><a href="#json"><span class="toc-section-number">13.4</span> JSON</a></li>
</ul></li>
<li><a href="#环境准备"><span class="toc-section-number">14</span> 环境准备</a><ul>
<li><a href="#laravel"><span class="toc-section-number">14.1</span> Laravel</a><ul>
<li><a href="#为什么是-laravel"><span class="toc-section-number">14.1.1</span> 为什么是 Laravel</a></li>
</ul></li>
<li><a href="#安装-laravel"><span class="toc-section-number">14.2</span> 安装 Laravel</a><ul>
<li><a href="#gnulinux安装composer"><span class="toc-section-number">14.2.1</span> GNU/Linux安装Composer</a></li>
</ul></li>
<li><a href="#mysql"><span class="toc-section-number">14.3</span> MySQL</a><ul>
<li><a href="#安装mysql-1"><span class="toc-section-number">14.3.1</span> 安装MySQL</a></li>
<li><a href="#配置mysql"><span class="toc-section-number">14.3.2</span> 配置MySQL</a></li>
</ul></li>
</ul></li>
<li><a href="#创建rest服务"><span class="toc-section-number">15</span> 创建REST服务</a><ul>
<li><a href="#数据库迁移"><span class="toc-section-number">15.1</span> 数据库迁移</a><ul>
<li><a href="#创建表"><span class="toc-section-number">15.1.1</span> 创建表</a></li>
<li><a href="#数据库迁移-1"><span class="toc-section-number">15.1.2</span> 数据库迁移</a></li>
</ul></li>
<li><a href="#创建restful"><span class="toc-section-number">15.2</span> 创建RESTful</a></li>
<li><a href="#laravel-resources"><span class="toc-section-number">15.3</span> Laravel Resources</a><ul>
<li><a href="#修改create"><span class="toc-section-number">15.3.1</span> 修改Create()</a></li>
<li><a href="#创建表单"><span class="toc-section-number">15.3.2</span> 创建表单</a></li>
<li><a href="#编辑模板"><span class="toc-section-number">15.3.3</span> 编辑模板</a></li>
</ul></li>
</ul></li>
<li><a href="#前端显示"><span class="toc-section-number">16</span> 前端显示</a><ul>
<li><a href="#库与车轮子"><span class="toc-section-number">16.1</span> 库与车轮子</a></li>
<li><a href="#库"><span class="toc-section-number">16.2</span> 库</a><ul>
<li><a href="#jquery"><span class="toc-section-number">16.2.1</span> jQuery</a></li>
<li><a href="#jquery-mobile"><span class="toc-section-number">16.2.2</span> jQuery Mobile</a></li>
</ul></li>
<li><a href="#网站前台显示"><span class="toc-section-number">16.3</span> 网站前台显示</a><ul>
<li><a href="#highcharts"><span class="toc-section-number">16.3.1</span> Highcharts</a></li>
<li><a href="#实时数据"><span class="toc-section-number">16.3.2</span> 实时数据</a></li>
</ul></li>
</ul></li>
<li><a href="#restful的coap协议"><span class="toc-section-number">17</span> RESTful的CoAP协议</a><ul>
<li><a href="#coap-嵌入式系统的rest"><span class="toc-section-number">17.1</span> CoAP: 嵌入式系统的REST</a></li>
<li><a href="#coap-命令行工具"><span class="toc-section-number">17.2</span> CoAP 命令行工具</a><ul>
<li><a href="#node-coap-cli"><span class="toc-section-number">17.2.1</span> Node CoAP CLI</a></li>
<li><a href="#libcoap"><span class="toc-section-number">17.2.2</span> libcoap</a></li>
<li><a href="#firefox-copper"><span class="toc-section-number">17.2.3</span> Firefox Copper</a></li>
</ul></li>
<li><a href="#coap-helloworld"><span class="toc-section-number">17.3</span> CoAP Hello,World</a></li>
<li><a href="#coap-数据库查询"><span class="toc-section-number">17.4</span> CoAP 数据库查询</a><ul>
<li><a href="#node-module"><span class="toc-section-number">17.4.1</span> Node Module</a></li>
<li><a href="#node-sqlite3"><span class="toc-section-number">17.4.2</span> Node-Sqlite3</a></li>
<li><a href="#查询数据"><span class="toc-section-number">17.4.3</span> 查询数据</a></li>
</ul></li>
<li><a href="#coap-block"><span class="toc-section-number">17.5</span> CoAP Block</a><ul>
<li><a href="#coap-post"><span class="toc-section-number">17.5.1</span> CoAP POST</a></li>
<li><a href="#coap-content-types"><span class="toc-section-number">17.5.2</span> CoAP Content Types</a></li>
</ul></li>
<li><a href="#coap-json"><span class="toc-section-number">17.6</span> CoAP JSON</a></li>
<li><a href="#使用iot-coap构建物联网"><span class="toc-section-number">17.7</span> 使用IoT-CoAP构建物联网</a></li>
</ul></li>
<li><a href="#简单物联网"><span class="toc-section-number">18</span> 简单物联网</a><ul>
<li><a href="#硬件通信"><span class="toc-section-number">18.1</span> 硬件通信</a><ul>
<li><a href="#串口通信-1"><span class="toc-section-number">18.1.1</span> 串口通信</a></li>
</ul></li>
<li><a href="#硬件"><span class="toc-section-number">18.2</span> 硬件</a><ul>
<li><a href="#arduino"><span class="toc-section-number">18.2.1</span> Arduino</a></li>
<li><a href="#继电器"><span class="toc-section-number">18.2.2</span> 继电器</a></li>
</ul></li>
</ul></li>
<li><a href="#android简单示例"><span class="toc-section-number">19</span> Android简单示例</a><ul>
<li><a href="#调用web-services-get"><span class="toc-section-number">19.1</span> 调用Web Services GET</a><ul>
<li><a href="#创建restclient"><span class="toc-section-number">19.1.1</span> 创建RESTClient</a></li>
</ul></li>
<li><a href="#使用rest-client获取结果"><span class="toc-section-number">19.2</span> 使用REST Client获取结果</a></li>
</ul></li>
<li><a href="#尾声"><span class="toc-section-number">20</span> 尾声</a><ul>
<li><a href="#路"><span class="toc-section-number">20.1</span> 路</a></li>
<li><a href="#其他-2"><span class="toc-section-number">20.2</span> 其他</a></li>
</ul></li>
</ul>
</div>
<p>本作品采用<a href="http://creativecommons.org/licenses/by-nc/4.0/">知识共享署名-非商业性使用 4.0 国际许可协议</a>进行许可。<img src="./images/88x31.png" alt="cc" /></p>
<p>© 2014 <a href="http://www.phodal.com">Phodal Huang</a>.</p>
<h1 id="前言"><span class="header-section-number">1</span> 前言</h1>
<p>设计物联网系统是件有意思的事情,它需要考虑到软件、硬件、通讯等多个不同方面。通过探索不同的语言,不同的框架,从而形成不同的解决方案。</p>
<p>在这里,我们将对设计物联网系统有一个简单的介绍,并探讨如何设计一个最小的物联网系统。</p>
<h2 id="目标读者"><span class="header-section-number">1.1</span> 目标读者</h2>
<p>目标读者: 初入物联网领域,希望对物联网系统有一个大概的认识和把握,并学会掌握一个基础的物联网系统的设计。</p>
<ul>
<li>硬件开发人员,对物联网有兴趣。</li>
<li>没有web开发经验</li>
<li>几乎为0的linux使用经验</li>
<li>想快速用于生产环境<br />
</li>
<li>对硬件了解有限的开发人员。</li>
<li>没接触过51、ARM、Arduino<br />
</li>
<li>想了解以下内容:</li>
<li>RESTful与IOT</li>
<li>CoAP协议</li>
<li>MQTT</li>
</ul>
<p>本文档对一些概念(如)只做了一些基本介绍,以方便读者理解。如果您想进一步了解这些知识,会列出一些推荐书目,以供参考。</p>
<h2 id="不适合人群"><span class="header-section-number">1.2</span> 不适合人群</h2>
<ul>
<li>如果你是在这方面已经有了丰富经验的开发者。</li>
<li>不是为了学习而学习这方面的知识。</li>
</ul>
<h2 id="介绍"><span class="header-section-number">1.3</span> 介绍</h2>
<p>关于内容的选择,这是一个有意思的话题,因为我们很难判断不同的开发者用的是怎样的语言,用的是怎样的框架。</p>
<p>于是我们便自作主张地选择了那些适合于理论学习的语言、框架、硬件,去除掉其他一些我们不需要考虑的因素,如语法,复杂度等等。当然,这些语言、框架、硬件也是最流行的。</p>
<ul>
<li>Arduino: 如果你从头开始学过硬件的话,那么你会爱上它的。</li>
<li>Raspberry PI: 如果你从头编译过GNU/Linux的话,我想你会爱上她的。</li>
<li>Python: 简单地来说,你可以方便地使用一些扩展,同时代码就表达了你的想法。</li>
<li>PHP : 这是一门容易部署的语言,我想你只需要在你的Ubuntu机器上,执行一下脚本就能完成安装了。而且,如果你是一个硬件开发者的话,你会更容易地找到其他开发者。</li>
<li>Javascript : 考虑到javascript这门语言已经无处不在了,而且会更加流行。所以,在这里CoAP、MQTT等版本是基于Nodejs的。</li>
<li>HTML、CSS : 这是必须的,同样,他们仍然无处不在。</li>
<li>GNU/Linux: 作为部署到服务器的一部分——你需要掌握他。当然如果你要用WAMP也是可以的。</li>
<li>CoAP: 用NodeJS构建IOT CoAP物联网</li>
</ul>
<h3 id="为什么没有c"><span class="header-section-number">1.3.1</span> 为什么没有C ?</h3>
<p><code>C都不懂还跑过来干嘛</code>。</p>
<h3 id="为什么不是java"><span class="header-section-number">1.3.2</span> 为什么不是JAVA ?</h3>
<p>大有以下两个原因</p>
<ul>
<li>学习JAVA的人很多,但是它不适合我们集中精力构建与学习,因为无关的代码太多了。</li>
<li>之前以及现在,我还是不喜欢JAVA (我更喜欢脚本语言,可以提高工作效率)。</li>
</ul>
<h2 id="如何阅读"><span class="header-section-number">1.4</span> 如何阅读</h2>
<p>这只是一个小小的建议,仅针对于在选择阅读上没有经验的读者。</p>
<table>
<thead>
<tr class="header">
<th>当前状态</th>
<th>建议</th>
</tr>
</thead>
<tbody>
<tr class="odd">
<td>软件初学者</td>
<td>从头阅读</td>
</tr>
<tr class="even">
<td>硬件开发者</td>
<td>从头阅读</td>
</tr>
<tr class="odd">
<td>没有web经验的开发者</td>
<td>从第二部分开始</td>
</tr>
</tbody>
</table>
<p>我们会在前面十章里简单介绍一些必要的基础知识,这些知识将会在后面我们构建物联网系统时用到。</p>
<p>某一天,正走在回学校的路上的我突然想到:“未来将会是一个科技的时代——虽然现在也是——只是在未来,科技将会无处不在。如果我们依旧对周围这些无处不在的代码一无所知的话,或许我们会成为黑客帝国之中被控制的普通人。”于是开始想着,有一天人们会像学习一门语言一样开始学习编程,直到又有一天我看到了学习编程如同学习一门语言的说法。这又恰好在我做完最小物联网系统之后,算是一个有趣的时间点,我开始想着像之前做最小物联网系统的那些步骤一样,写一个简单的入门。也可以补充好之前在这个最小物联网系统缺失的那些东西,给那些正在开始试图去解决编程问题的人。</p>
<p>让我们先从身边的语言下手,也就是现在无处不在的html+javascript+css。</p>
<h1 id="无处不在的html"><span class="header-section-number">2</span> 无处不在的HTML</h1>
<p>之所以从html开始,是因为我们不需要配置一个复杂的开发环境,也许你还不知道开发环境是什么东西,不过这也没关系,毕竟这些知识需要慢慢的接触才能有所了解,尤其是对于普通的业余爱好者来说,当然,对于专业选手言自然不是问题。HTML是Web的核心语言,也算是比较基础的语言。</p>
<h2 id="html的helloworld"><span class="header-section-number">2.1</span> html的hello,world</h2>
<p>Hello,world是一个传统,所以在这里也遵循这个有趣的传统,我们所要做的事情其实很简单,虽然也有一点点hack的感觉。——让我们先来新建一个文并命名为“helloworld.html”。</p>
<p>(PS:大部分人应该都是在windows环境下工作的,所以你需要新建一个文本,然后重命名,或者你需要一个编辑器,在这里我们推荐用<strong>sublime text</strong>。破解不破解,注册不注册都不会对你的使用有太多的影响。)</p>
<ol style="list-style-type: decimal">
<li><p>新建文件</p></li>
<li>输入
<pre><code class="html">hello,world</code></pre></li>
<li><p>保存为->“helloworld.html”,</p></li>
<li><p>双击打开这个文件。 正常情况下都应该是用你的默认浏览器打开。只要是一个正常工作的现代浏览器,都应该可以看到上面显示的是“Hello,world”。</p></li>
</ol>
<p>这才是最短的hello,world程序,但是呢?在ruby中会是这样子的</p>
<div class="sourceCode"><pre class="sourceCode bash"><code class="sourceCode bash"><span class="kw">2.0.0-p353</span> :001 <span class="kw">></span> p <span class="st">"hello,world"</span>
<span class="st">"hello,world"</span>
=<span class="kw">></span> <span class="st">"hello,world"</span>
<span class="kw">2.0.0-p353</span> :002 <span class="kw">></span></code></pre></div>
<p>等等,如果你了解过html的话,会觉得这一点都不符合语法规则,但是他工作了,没有什么比安装完Nginx后看到It works!更让人激动了。</p>
<p>遗憾的是,它可能无法在所有的浏览器上工作,所以我们需要去调试其中的bug。</p>
<h3 id="调试helloworld"><span class="header-section-number">2.1.1</span> 调试hello,world</h3>
<p>我们会发现我们的代码在浏览器中变成了下面的代码,如果你和我一样用的是chrome,那么你可以右键浏览器中的空白区域,点击审查元素,就会看到下面的代码。</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="kw"><html></span>
<span class="kw"><head></head></span>
<span class="kw"><body></span>hello,world<span class="kw"></body></span>
<span class="kw"></html></span></code></pre></div>
<p>这个才是真正能在大部分浏览器上工作的代码,所以复制它到编辑器里吧。</p>
<h3 id="说说helloworld"><span class="header-section-number">2.1.2</span> 说说hello,world</h3>
我很不喜欢其中的<*></*>,但是我也没有找到别的方法来代替它们,所以这是一个设计得当的语言。甚至大部分人都说这算不上是一门真正的语言,不过html的原义是
<blockquote>
超文本标记语言
</blockquote>
<p>所以我们可以发现其中的关键词是标记——markup,也就是说html是一个markup,head是一个markup,body也是一个markup。</p>
<p>然而,我们真正工作的代码是在body里面,至于为什么是在这里面,这个问题就太复杂了。打个比方来说:</p>
<ol style="list-style-type: decimal">
<li><p>我们所使用的汉语是人类用智慧创造的,我们所正在学的这门语言同样也是人类创造的。</p></li>
<li><p>我们在自己的语言里遵循着<strong>桌子是桌子,凳子是凳子</strong>的原则,很少有人会问为什么。</p></li>
</ol>
<h3 id="想用中文"><span class="header-section-number">2.1.3</span> 想用中文?</h3>
<p>所以我们也可以把计算机语言与现实世界里用于交流沟通的语言划上一个等号。而我们所要学习的语言,并不是我们最熟悉的汉语语言,所以我们便觉得这些很复杂,但是如果我们试着用汉语替换掉上面的代码的话</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="er"><</span>语言>
<span class="er"><</span>头><span class="er"><</span>结束头>
<span class="er"><</span>身体>你好,世界<span class="er"><</span>结束身体>
<span class="er"><</span>结束语言></code></pre></div>
<p>这看上去很奇怪,只是因为是直译过去的原因,也许你会觉得这样会好理解一点,但是输入上可就一点儿也不方便,因为这键盘本身就不适合我们去输入汉字,同时也意味着可能你输入的会有问题。</p>
<p>让我们把上面的代码代替掉原来的代码然后保存,打开浏览器会看到下面的结果</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="er"><</span>语言> <span class="er"><</span>头><span class="er"><</span>结束头> <span class="er"><</span>身体>你好,世界<span class="er"><</span>结束身体> <span class="er"><</span>结束语言></code></pre></div>
<p>更不幸的结果可能是</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="er"><</span>璇█> <span class="er"><</span>澶�><span class="er"><</span>缁撴潫澶�> <span class="er"><</span>韬綋>浣犲ソ锛屼笘鐣�<span class="er"><</span>缁撴潫韬綋> <span class="er"><</span>缁撴潫璇█></code></pre></div>
<p>这是一个编码问题,对中文支持不友好。</p>
<p>我们把上面的代码改为和标记语言一样的结构</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="er"><</span>语言>
<span class="er"><</span>头><span class="er"><</span>/头>
<span class="er"><</span>身体>你好,世界<span class="er"><</span>/身体>
<span class="er"><</span>结束语言></code></pre></div>
<p>于是我们看到的结果便是</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="er"><</span>语言> <span class="er"><</span>头> <span class="er"><</span>身体>你好,世界</code></pre></div>
<p>被chrome浏览器解析成什么样了?</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="kw"><html><head></head><body></span><span class="er"><</span>语言>
<span class="er"><</span>头><span class="co"><!--头--></span>
<span class="er"><</span>身体>你好,世界<span class="co"><!--身体--></span>
<span class="co"><!--语言--></span>
<span class="kw"></body></html></span> </code></pre></div>
<p>以 <!--开头,--></p>
<p>结尾的是注释,写给人看的代码,不是给机器看的,所以机器不会去理解这些代码。</p>
<p>但是当我们把代码改成</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="kw"><whatwewanttosay></span>你好世界<span class="kw"></whatwewanttosay></span></code></pre></div>
<p>浏览器上面显示的内容就变成了</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html">你好世界</code></pre></div>
<p>或许你会觉得很神奇,但是这一点儿也不神奇,虽然我们的中文语法也遵循着标记语言的标准,但是我们的浏览器不支持中文标记。</p>
<p>结论:</p>
<ol style="list-style-type: decimal">
<li>浏览器对中文支持不友好。</li>
<li>浏览器对英文支持友好。</li>
</ol>
<p>刚开始的时候不要对中文编程有太多的想法,这是很不现实的:</p>
<ol style="list-style-type: decimal">
<li>现有的系统都是基于英语语言环境构建的,对中文支持不是很友好。</li>
<li>中文输入的速度在某种程度上来说没有英语快。</li>
</ol>
<p>我们离开话题已经很远了,但是这里说的都是针对于那些不满于英语的人来说的,只有当我们可以从头构建一个中文系统的时候才是可行的,而这些就要将cpu、软件、硬件都包含在内,甚至我们还需要考虑重新设计cpu的结构,在某种程度上来说会有些不现实。或许,需要一代又一代人的努力。忘记那些吧,师夷长之技以治夷。</p>
<h2 id="其他html标记"><span class="header-section-number">2.2</span> 其他html标记</h2>
<p>添加一个标题,</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"><title></span>标题<span class="kw"></title></span>
<span class="kw"></head></span>
<span class="kw"><body></span>hello,world<span class="kw"></body></span>
<span class="kw"></html></span></code></pre></div>
<p>我们便可以在浏览器的最上方看到“标题”二字,就像我们常用的淘宝网,也包含了上面的东西,只是还包括了更多的东西,所以你也可以看懂那些我们可以看到的淘宝的标题。</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"><title></span>标题<span class="kw"></title></span>
<span class="kw"></head></span>
<span class="kw"><body></span>
hello,world
<span class="kw"><h1></span>大标题<span class="kw"></h1></span>
<span class="kw"><h2></span>次标题<span class="kw"></h2></span>
<span class="kw"><h3></span>...<span class="kw"></h3></span>
<span class="kw"><ul></span>
<span class="kw"><li></span>列表1<span class="kw"></li></span>
<span class="kw"><li></span>列表2<span class="kw"></li></span>
<span class="kw"></ul></span>
<span class="kw"></body></span>
<span class="kw"></html></span></code></pre></div>
<p>更多的东西可以在一些书籍上看到,这边所要说的只是一次简单的语言入门,其他的东西都和这些类似。</p>
<h3 id="美妙之处"><span class="header-section-number">2.2.1</span> 美妙之处</h3>
<p>我们简单地上手了一门不算是语言的语言,浏览器简化了这其中的大部分过程,虽然没有C和其他语言来得有专业感,但是我们试着去开始写代码了。我们可能在未来的某一篇中可能会看到类似的语言,诸如python,我们所要做的就是</p>
<div class="sourceCode"><pre class="sourceCode bash"><code class="sourceCode bash">$ <span class="kw">python</span> file.py
=<span class="kw">>hello</span>,world</code></pre></div>
<p>然后在终端上返回结果。只是因为在我看来学会html是有意义的,简单的上手,然后再慢慢地深入,如果一开始我们就去理解指针,开始去理解类。我们甚至还知道程序是怎么编译运行的时候,在这个过程中又发生了什么。虽然现在我们也没能理解这其中发生了什么,但是至少展示了</p>
<ol style="list-style-type: decimal">
<li>中文编程语言在当前意义不大,不现实,效率不高兼容性差</li>
<li>语言的语法是固定的。(ps:虽然我们也可以进行扩充,我们将会在后来支持上述的中文标记。)</li>
<li>已经开始写代码,而不是还在配置开发环境。</li>
<li>随身的工具才是最好的,最常用的code也才是实在的。</li>
</ol>
<h3 id="更多"><span class="header-section-number">2.2.2</span> 更多</h3>
<p>我们还没有试着去解决“某商店里的糖一颗5块钱,小明买了3颗糖,小明一共花了多少钱”的问题。也就是说我们学会的是一个还不能解决实际问题的语言,于是我们还需要学点东西,比如javascript,css。我们可以将Javascript理解为解决问题的语言,html则是前端显示,css是配置文件,这样的话,我们会在那之后学会成为一个近乎专业的程序员。我们刚刚学习了一下怎么在前端显示那些代码的行为,于是我们还需要Javascript。</p>
<h1 id="无处不在的javascript"><span class="header-section-number">3</span> 无处不在的Javascript</h1>
<p>Javascript现在已经无处不在了,也许你正打开的某个网站,他便可能是node.js+json+javascript+mustache.js完成的,虽然你还没理解上面那些是什么,也正是因为你不理解才需要去学习更多的东西。但是你只要知道Javascript已经无处不在了,它可能就在你手机上的某个app里,就在你浏览的网页里,就运行在你IDE中的某个进程里。</p>
<h2 id="javascript的helloworld"><span class="header-section-number">3.1</span> Javascript的Hello,world</h2>
<p>这里我们还需要有一个helloworld.html,Javascript是专为网页交互而设计的脚本语言,所以我们一点点来开始这部分的旅途,先写一个符合标准的helloworld.html</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="dt"><!DOCTYPE </span>html<span class="dt">></span>
<span class="kw"><html></span>
<span class="kw"><head></head></span>
<span class="kw"><body></body></span>
<span class="kw"></html></span></code></pre></div>
<p>然后开始融入我们的javascript,向HTML中插入Javascript的方法,就需要用到html中的<script>标签,我们先用页面嵌入的方法来写helloworld。</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="dt"><!DOCTYPE </span>html<span class="dt">></span>
<span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"><script></span>
<span class="va">document</span>.<span class="at">write</span>(<span class="st">'hello,world'</span>)<span class="op">;</span>
<span class="op"><</span><span class="ss">/script></span>
<span class="ss"> </head</span><span class="op">></span>
<span class="op"><</span>body<span class="op">><</span><span class="ss">/body></span>
<span class="ss"></html</span><span class="op">></span></code></pre></div>
<p>按照标准的写法,我们还需要声明这个脚本的类型</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="dt"><!DOCTYPE </span>html<span class="dt">></span>
<span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"><script</span><span class="ot"> type=</span><span class="st">"text/javascript"</span><span class="kw">></span>
<span class="va">document</span>.<span class="at">write</span>(<span class="st">'hello,world'</span>)<span class="op">;</span>
<span class="op"><</span><span class="ss">/script></span>
<span class="ss"> </head</span><span class="op">></span>
<span class="op"><</span>body<span class="op">><</span><span class="ss">/body></span>
<span class="ss"></html</span><span class="op">></span></code></pre></div>
<p>没有显示hello,world?试试下面的代码</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="dt"><!DOCTYPE </span>html<span class="dt">></span>
<span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"><script</span><span class="ot"> type=</span><span class="st">"text/javascript"</span><span class="kw">></span>
<span class="va">document</span>.<span class="at">write</span>(<span class="st">'hello,world'</span>)<span class="op">;</span>
<span class="op"><</span><span class="ss">/script></span>
<span class="ss"> </head</span><span class="op">></span>
<span class="op"><</span>body<span class="op">></span>
<span class="op"><</span>noscript<span class="op">></span>
disable Javascript
<span class="op"><</span><span class="ss">/noscript></span>
<span class="ss"> </body</span><span class="op">></span>
<span class="op"><</span><span class="ss">/html></span></code></pre></div>
<h2 id="更js一点"><span class="header-section-number">3.2</span> 更js一点</h2>
<p>我们需要让我们的代码看上去更像是js,同时是以js结尾。就像C语言的源码是以C结尾的,我们也同样需要让我们的代码看上去更正式一点。于是我们需要在helloworld.html的同一文件夹下创建一个app.js文件,在里面写着</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="va">document</span>.<span class="at">write</span>(<span class="st">'hello,world'</span>)<span class="op">;</span></code></pre></div>
<p>同时我们的helloworld.html还需要告诉我们的浏览器js代码在哪里</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="dt"><!DOCTYPE </span>html<span class="dt">></span>
<span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"><script</span><span class="ot"> type=</span><span class="st">"text/javascript"</span><span class="ot"> src=</span><span class="st">"app.js"</span><span class="kw">></script></span>
<span class="kw"></head></span>
<span class="kw"><body></span>
<span class="kw"><noscript></span>
disable Javascript
<span class="kw"></noscript></span>
<span class="kw"></body></span>
<span class="kw"></html></span></code></pre></div>
<h3 id="从数学出发"><span class="header-section-number">3.2.1</span> 从数学出发</h3>
<p>让我们回到第一章讲述的小明的问题,<strong>从实际问题下手编程,更容易学会编程</strong>。小学时代的数学题最喜欢这样子了——某商店里的糖一个5块钱,小明买了3个糖,小明一共花了多少钱。在编程方面,也许我们还算是小学生。最直接的方法就是直接计算3x5=?</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="va">document</span>.<span class="at">write</span>(<span class="dv">3</span><span class="op">*</span><span class="dv">5</span>)<span class="op">;</span></code></pre></div>
<p>document.write实际也我们可以理解为输出,也就是往页面里写入3*5的结果,在有双引号的情况下会输出字符串。我们便会在浏览器上看到15,这便是一个好的开始,也是一个糟糕的开始。</p>
<h2 id="设计和编程"><span class="header-section-number">3.3</span> 设计和编程</h2>
<p>对于实际问题,如果我们只是止于所要得到的结果,很多年之后,我们就成为了code monkey。对这个问题进行再一次设计,所谓的设计有些时候会把简单的问题复杂化,有些时候会使以后的扩展更加简单。这一天因为这家商店的糖价格太高了,于是店长将价格降为了4块钱。</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="va">document</span>.<span class="at">write</span>(<span class="dv">3</span><span class="op">*</span><span class="dv">4</span>)<span class="op">;</span></code></pre></div>
<p>于是我们又得到了我们的结果,但是下次我们看到这些代码的时候没有分清楚哪个是糖的数量,哪个是价格,于是我们重新设计了程序</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript">tang<span class="op">=</span><span class="dv">4</span><span class="op">;</span>
num<span class="op">=</span><span class="dv">3</span><span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(tang<span class="op">*</span>num)<span class="op">;</span></code></pre></div>
<p>这才能叫得上是程序设计,或许你注意到了“;”这个符号的存在,我想说的是这是另外一个标准,我们不得不去遵守,也不得不去fuck。</p>
<h3 id="函数"><span class="header-section-number">3.3.1</span> 函数</h3>
<p>记得刚开始学三角函数的时候,我们会写</p>
<pre><code>sin 30=0.5</code></pre>
<p>而我们的函数也是类似于此,换句话说,因为很多搞计算机的先驱都学好了数学,都把数学世界的规律带到了计算机世界,所以我们的函数也是类似于此,让我们做一个简单的开始。</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">function</span> <span class="at">hello</span>()<span class="op">{</span>
<span class="cf">return</span> <span class="va">document</span>.<span class="at">write</span>(<span class="st">"hello,world"</span>)<span class="op">;</span>
<span class="op">}</span>
<span class="at">hello</span>()<span class="op">;</span></code></pre></div>
<p>当我第一次看到函数的时候,有些小激动终于出现了。我们写了一个叫hello的函数,它返回了往页面中写入hello,world的方法,然后我们调用了hello这个函数,于是页面上有了hello,world。</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">function</span> <span class="at">sin</span>(degree)<span class="op">{</span>
<span class="cf">return</span> <span class="va">document</span>.<span class="at">write</span>(<span class="va">Math</span>.<span class="at">sin</span>(degree))<span class="op">;</span>
<span class="op">}</span>
<span class="at">sin</span>(<span class="dv">30</span>)<span class="op">;</span></code></pre></div>
<p>在这里degree就称之为变量。 于是输出了-0.9880316240928602,而不是0.5,因为这里用的是弧度制,而不是角度制。</p>
<pre><code>sin(30)</code></pre>
<p>的输出结果有点类似于sin 30。写括号的目的在于,括号是为了方便解析,这个在不同的语言中可能是不一样的,比如在ruby中我们可以直接用类似于数学中的表达:</p>
<div class="sourceCode"><pre class="sourceCode ruby"><code class="sourceCode ruby"><span class="fl">2.0</span>.<span class="dv">0</span>-p353 :<span class="dv">004</span> > <span class="dt">Math</span>.sin <span class="dv">30</span>
=> -<span class="fl">0.9880316240928618</span>
<span class="fl">2.0</span>.<span class="dv">0</span>-p353 :<span class="dv">005</span> ></code></pre></div>
<p>我们可以在函数中传入多个变量,于是我们再回到小明的问题,就会这样去编写代码。</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">function</span> <span class="at">calc</span>(tang<span class="op">,</span>num)<span class="op">{</span>
result<span class="op">=</span>tang<span class="op">*</span>num<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(result)<span class="op">;</span>
<span class="op">}</span>
<span class="at">calc</span>(<span class="dv">3</span><span class="op">,</span><span class="dv">4</span>)<span class="op">;</span></code></pre></div>
<p>但是从某种程度上来说,我们的calc做了计算的事又做了输出的事,总的来说设计上有些不好。</p>
<h3 id="重新设计"><span class="header-section-number">3.3.2</span> 重新设计</h3>
<p>我们将输出的工作移到函数的外面,</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">function</span> <span class="at">calc</span>(tang<span class="op">,</span>num)<span class="op">{</span>
<span class="cf">return</span> tang<span class="op">*</span>num<span class="op">;</span>
<span class="op">}</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="at">calc</span>(<span class="dv">3</span><span class="op">,</span><span class="dv">4</span>))<span class="op">;</span></code></pre></div>
<p>接着我们用一种更有意思的方法来写这个问题的解决方案</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">function</span> <span class="at">calc</span>(tang<span class="op">,</span>num)<span class="op">{</span>
<span class="cf">return</span> tang<span class="op">*</span>num<span class="op">;</span>
<span class="op">}</span>
<span class="kw">function</span> <span class="at">printResult</span>(tang<span class="op">,</span>num)<span class="op">{</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="at">calc</span>(tang<span class="op">,</span>num))<span class="op">;</span>
<span class="op">}</span>
<span class="at">printResult</span>(<span class="dv">3</span><span class="op">,</span> <span class="dv">4</span>)</code></pre></div>
<p>看上去更专业了一点点,如果我们只需要计算的时候我们只需要调用calc,如果我们需要输出的时候我们就调用printResult的方法。</p>
<h3 id="object和函数"><span class="header-section-number">3.3.3</span> object和函数</h3>
<p>我们还没有说清楚之前我们遇到过的document.write以及Math.sin的语法为什么看上去很奇怪,所以让我们看看他们到底是什么,修改app.js为以下内容</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="va">document</span>.<span class="at">write</span>(<span class="kw">typeof</span> document)<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="kw">typeof</span> Math)<span class="op">;</span></code></pre></div>
<p>typeof document会返回document的数据类型,就会发现输出的结果是</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript">object object</code></pre></div>
<p>所以我们需要去弄清楚什么是object。对象的定义是</p>
<blockquote>
无序属性的集合,其属性可以包含基本值、对象或者函数。
</blockquote>
<p>创建一个object,然后观察这便是我们接下来要做的</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript">store<span class="op">={};</span>
<span class="va">store</span>.<span class="at">tang</span><span class="op">=</span><span class="dv">4</span><span class="op">;</span>
<span class="va">store</span>.<span class="at">num</span><span class="op">=</span><span class="dv">3</span><span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="va">store</span>.<span class="at">tang</span><span class="op">*</span><span class="va">store</span>.<span class="at">num</span>)<span class="op">;</span></code></pre></div>
<p>我们就有了和document.write一样的用法,这也是对象的美妙之处,只是这里的对象只是包含着基本值,因为</p>
<pre><code>typeof story.tang="number"</code></pre>
<p>一个包含对象的对象应该是这样子的。</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript">store<span class="op">={};</span>
<span class="va">store</span>.<span class="at">tang</span><span class="op">=</span><span class="dv">4</span><span class="op">;</span>
<span class="va">store</span>.<span class="at">num</span><span class="op">=</span><span class="dv">3</span><span class="op">;</span>
<span class="va">document</span>.<span class="at">writeln</span>(<span class="va">store</span>.<span class="at">tang</span><span class="op">*</span><span class="va">store</span>.<span class="at">num</span>)<span class="op">;</span>
<span class="kw">var</span> wall<span class="op">=</span><span class="kw">new</span> <span class="at">Object</span>()<span class="op">;</span>
<span class="va">wall</span>.<span class="at">store</span><span class="op">=</span>store<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="kw">typeof</span> <span class="va">wall</span>.<span class="at">store</span>)<span class="op">;</span></code></pre></div>
<p>而我们用到的document.write和上面用到的document.writeln都是属于这个无序属性集合中的函数。</p>
<p>下面代码说的就是这个无序属性集中中的函数。</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">var</span> IO<span class="op">=</span><span class="kw">new</span> <span class="at">Object</span>()<span class="op">;</span>
<span class="kw">function</span> <span class="at">print</span>(result)<span class="op">{</span>
<span class="va">document</span>.<span class="at">write</span>(result)<span class="op">;</span>
<span class="op">};</span>
<span class="va">IO</span>.<span class="at">print</span><span class="op">=</span>print<span class="op">;</span>
<span class="va">IO</span>.<span class="at">print</span>(<span class="st">"a obejct with function"</span>)<span class="op">;</span>
<span class="va">IO</span>.<span class="at">print</span>(<span class="kw">typeof</span> <span class="va">IO</span>.<span class="at">print</span>)<span class="op">;</span></code></pre></div>
<p>我们定义了一个叫IO的对象,声明对象可以用</p>
<pre><code>var store={};</code></pre>
<p>又或者是</p>
<pre><code>var store=new Object{};</code></pre>
<p>两者是等价的,但是用后者的可读性会更好一点,我们定义了一个叫print的函数,他的作用也就是document.write,IO中的print函数是等价于print()函数,这也就是对象和函数之间的一些区别,对象可以包含函数,对象是无序属性的集合,其属性可以包含基本值、对象或者函数。</p>
<p>复杂一点的对象应该是下面这样的一种情况。</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">var</span> Person<span class="op">={</span><span class="dt">name</span><span class="op">:</span><span class="st">"phodal"</span><span class="op">,</span><span class="dt">weight</span><span class="op">:</span><span class="dv">50</span><span class="op">,</span><span class="dt">height</span><span class="op">:</span><span class="dv">166</span><span class="op">};</span>
<span class="kw">function</span> <span class="at">dream</span>()<span class="op">{</span>
future<span class="op">;</span>
<span class="op">};</span>
<span class="va">Person</span>.<span class="at">future</span><span class="op">=</span>dream<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="kw">typeof</span> Person)<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="va">Person</span>.<span class="at">future</span>)<span class="op">;</span></code></pre></div>
<p>而这些会在我们未来的实际编程过程中用得更多。</p>
<h3 id="面向对象"><span class="header-section-number">3.3.4</span> 面向对象</h3>
<p>开始之前先让我们简化上面的代码,</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="va">Person</span>.<span class="at">future</span><span class="op">=</span><span class="kw">function</span> <span class="at">dream</span>()<span class="op">{</span>
future<span class="op">;</span>
<span class="op">}</span></code></pre></div>
<p>看上去比上面的简单多了,不过我们还可以简化为下面的代码。。。</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">var</span> Person<span class="op">=</span><span class="kw">function</span>()<span class="op">{</span>
<span class="kw">this</span>.<span class="at">name</span><span class="op">=</span><span class="st">"phodal"</span><span class="op">;</span>
<span class="kw">this</span>.<span class="at">weight</span><span class="op">=</span><span class="dv">50</span><span class="op">;</span>
<span class="kw">this</span>.<span class="at">height</span><span class="op">=</span><span class="dv">166</span><span class="op">;</span>
<span class="kw">this</span>.<span class="at">future</span><span class="op">=</span><span class="kw">function</span> <span class="at">dream</span>()<span class="op">{</span>
<span class="cf">return</span> <span class="st">"future"</span><span class="op">;</span>
<span class="op">};</span>
<span class="op">};</span>
<span class="kw">var</span> person<span class="op">=</span><span class="kw">new</span> <span class="at">Person</span>()<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="va">person</span>.<span class="at">name</span><span class="op">+</span><span class="st">"<br>"</span>)<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="kw">typeof</span> person<span class="op">+</span><span class="st">"<br>"</span>)<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="kw">typeof</span> <span class="va">person</span>.<span class="at">future</span><span class="op">+</span><span class="st">"<br>"</span>)<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="va">person</span>.<span class="at">future</span>()<span class="op">+</span><span class="st">"<br>"</span>)<span class="op">;</span></code></pre></div>
<p>只是在这个时候Person是一个函数,但是我们声明的person却变成了一个对象<strong>一个Javascript函数也是一个对象,并且,所有的对象从技术上讲也只不过是函数。</strong>这里的“<br>”是HTML中的元素,称之为DOM,在这里起的是换行的作用,我们会在稍后介绍它,这里我们先关心下this。this关键字表示函数的所有者或作用域,也就是这里的Person。</p>
<p>上面的方法显得有点不可取,换句话说和一开始的</p>
<pre><code>document.write(3*4);</code></pre>
<p>一样,不具有灵活性,因此在我们完成功能之后,我们需要对其进行优化,这就是程序设计的真谛——解决完实际问题后,我们需要开始真正的设计,而不是解决问题时的编程。</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">var</span> Person<span class="op">=</span><span class="kw">function</span>(name<span class="op">,</span>weight<span class="op">,</span>height)<span class="op">{</span>
<span class="kw">this</span>.<span class="at">name</span><span class="op">=</span>name<span class="op">;</span>
<span class="kw">this</span>.<span class="at">weight</span><span class="op">=</span>weight<span class="op">;</span>
<span class="kw">this</span>.<span class="at">height</span><span class="op">=</span>height<span class="op">;</span>
<span class="kw">this</span>.<span class="at">future</span><span class="op">=</span><span class="kw">function</span>()<span class="op">{</span>
<span class="cf">return</span> <span class="st">"future"</span><span class="op">;</span>
<span class="op">};</span>
<span class="op">};</span>
<span class="kw">var</span> phodal<span class="op">=</span><span class="kw">new</span> <span class="at">Person</span>(<span class="st">"phodal"</span><span class="op">,</span><span class="dv">50</span><span class="op">,</span><span class="dv">166</span>)<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="va">phodal</span>.<span class="at">name</span><span class="op">+</span><span class="st">"<br>"</span>)<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="va">phodal</span>.<span class="at">weight</span><span class="op">+</span><span class="st">"<br>"</span>)<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="va">phodal</span>.<span class="at">height</span><span class="op">+</span><span class="st">"<br>"</span>)<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="va">phodal</span>.<span class="at">future</span>()<span class="op">+</span><span class="st">"<br>"</span>)<span class="op">;</span></code></pre></div>
<p>于是,产生了这样一个可重用的Javascript对象,this关键字确立了属性的所有者。</p>
<h2 id="其他"><span class="header-section-number">3.4</span> 其他</h2>
<p>Javascript还有一个很强大的特性,也就是原型继承,不过这里我们先不考虑这些部分,用尽量少的代码及关键字来实际我们所要表达的核心功能,这才是这里的核心,其他的东西我们可以从其他书本上学到。</p>
<p>所谓的继承,</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">var</span> Chinese<span class="op">=</span><span class="kw">function</span>()<span class="op">{</span>
<span class="kw">this</span>.<span class="at">country</span><span class="op">=</span><span class="st">"China"</span><span class="op">;</span>
<span class="op">}</span>
<span class="kw">var</span> Person<span class="op">=</span><span class="kw">function</span>(name<span class="op">,</span>weight<span class="op">,</span>height)<span class="op">{</span>
<span class="kw">this</span>.<span class="at">name</span><span class="op">=</span>name<span class="op">;</span>
<span class="kw">this</span>.<span class="at">weight</span><span class="op">=</span>weight<span class="op">;</span>
<span class="kw">this</span>.<span class="at">height</span><span class="op">=</span>height<span class="op">;</span>
<span class="kw">this</span>.<span class="at">futrue</span><span class="op">=</span><span class="kw">function</span>()<span class="op">{</span>
<span class="cf">return</span> <span class="st">"future"</span><span class="op">;</span>
<span class="op">}</span>
<span class="op">}</span>
<span class="va">Chinese</span>.<span class="at">prototype</span><span class="op">=</span><span class="kw">new</span> <span class="at">Person</span>()<span class="op">;</span>
<span class="kw">var</span> phodal<span class="op">=</span><span class="kw">new</span> <span class="at">Chinese</span>(<span class="st">"phodal"</span><span class="op">,</span><span class="dv">50</span><span class="op">,</span><span class="dv">166</span>)<span class="op">;</span>
<span class="va">document</span>.<span class="at">write</span>(<span class="va">phodal</span>.<span class="at">country</span>)<span class="op">;</span></code></pre></div>
<p>完整的Javascript应该由下列三个部分组成:</p>
<ul>
<li>核心(ECMAScript)——核心语言功能</li>
<li>文档对象模型(DOM)——访问和操作网页内容的方法和接口</li>
<li>浏览器对象模型(BOM)——与浏览器交互的方法和接口</li>
</ul>
<p>我们在上面讲的都是ECMAScript,也就是语法相关的,但是JS真正强大的,或者说我们最需要的可能就是对DOM的操作,这也就是为什么jQuery等库可以流行的原因之一,而核心语言功能才是真正在哪里都适用的,至于BOM,真正用到的机会很少,因为没有完善的统一的标准。</p>
<p>一个简单的DOM示例,</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="dt"><!DOCTYPE </span>html<span class="dt">></span>
<span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"></head></span>
<span class="kw"><body></span>
<span class="kw"><noscript></span>
disable Javascript
<span class="kw"></noscript></span>
<span class="kw"><p</span><span class="ot"> id=</span><span class="st">"para"</span><span class="ot"> style=</span><span class="st">"color:red"</span><span class="kw">></span>Red<span class="kw"></p></span>
<span class="kw"></body></span>
<span class="kw"><script</span><span class="ot"> type=</span><span class="st">"text/javascript"</span><span class="ot"> src=</span><span class="st">"app.js"</span><span class="kw">></script></span>
<span class="kw"></html></span></code></pre></div>
<p>我们需要修改一下helloworld.html添加</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="kw"><p</span><span class="ot"> id=</span><span class="st">"para"</span><span class="ot"> style=</span><span class="st">"color:red"</span><span class="kw">></span>Red<span class="kw"></p></span></code></pre></div>
<p>同时还需要将script标签移到body下面,如果没有意外的话我们会看到页面上用红色的字体显示Red,修改app.js。</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">var</span> para<span class="op">=</span><span class="va">document</span>.<span class="at">getElementById</span>(<span class="st">"para"</span>)<span class="op">;</span>
<span class="va">para</span>.<span class="va">style</span>.<span class="at">color</span><span class="op">=</span><span class="st">"blue"</span><span class="op">;</span></code></pre></div>
<p>接着,字体就变成了蓝色,有了DOM我们就可以对页面进行操作,可以说我们看到的绝大部分的页面效果都是通过DOM操作实现的。</p>
<h2 id="美妙之处-1"><span class="header-section-number">3.5</span> 美妙之处</h2>
<p>这里说到的Javascript仅仅只是其中的一小小部分,忽略掉的东西很多,只关心的是如何去设计一个实用的app,作为一门编程语言,他还有其他强大的内制函数,要学好需要一本有价值的参考书。这里提到的只是其中的不到20%的东西,其他的80%或者更多会在你解决问题的时候出现。</p>
<ul>
<li>我们可以创建一个对象或者函数,它可以包含基本值、对象或者函数。</li>
<li>我们可以用Javascript修改页面的属性,虽然只是简单的示例。</li>
<li>我们还可以去解决实际的编程问题。</li>
</ul>
<h1 id="无处不在的css"><span class="header-section-number">4</span> 无处不在的CSS</h1>
<p>或许你觉得CSS一点儿也不重要,而事实上,如果说HTML是建筑的框架,CSS就是房子的装修。那么Javascript呢,我听到的最有趣的说法是小三——还是先让我们回到代码上来吧。</p>
<h2 id="css"><span class="header-section-number">4.1</span> CSS</h2>
<p>下面就是我们之前说到的代码,css将Red三个字母变成了红色。</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="dt"><!DOCTYPE </span>html<span class="dt">></span>
<span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"></head></span>
<span class="kw"><body></span>
<span class="kw"><p</span><span class="ot"> id=</span><span class="st">"para"</span><span class="ot"> style=</span><span class="st">"color:red"</span><span class="kw">></span>Red<span class="kw"></p></span>
<span class="kw"></body></span>
<span class="kw"><script</span><span class="ot"> type=</span><span class="st">"text/javascript"</span><span class="ot"> src=</span><span class="st">"app.js"</span><span class="kw">></script></span>
<span class="kw"></html></span></code></pre></div>
<p>只是,</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">var</span> para<span class="op">=</span><span class="va">document</span>.<span class="at">getElementById</span>(<span class="st">"para"</span>)<span class="op">;</span>
<span class="va">para</span>.<span class="va">style</span>.<span class="at">color</span><span class="op">=</span><span class="st">"blue"</span><span class="op">;</span></code></pre></div>
<p>将字体变成了蓝色,CSS+HTML让页面有序的工作着,但是Javascript却打乱了这些秩序,有着唯恐世界不乱的精彩,也难怪被冠以小三之名了——或许终于可以理解,为什么以前人们对于Javascript没有好感了——不过这里要讲的是正室,也就是CSS,这时还没有Javascript。</p>
<div class="figure">
<img src="./images/redfonts.png" alt="Red Fonts" />
<p class="caption">Red Fonts</p>
</div>
<h2 id="关于css"><span class="header-section-number">4.2</span> 关于CSS</h2>
<p>这不是一篇专业讲述CSS的书籍,所以我不会去说CSS是怎么来的,有些东西我们既然可以很容易从其他地方知道,也就不需要花太多时间去重复。诸如重构等这些的目的之一也在于去除重复的代码,不过有些重复是不可少的,也是有必要的,而通常这些东西可能是由其他地方复制过来的。</p>
<p>到目前为止我们没有依赖于任何特殊的硬件或者是软件,对于我们来说我们最基本的需求就是一台电脑,或者可以是你的平板电脑,当然也可以是你的智能手机,因为他们都有个浏览器,而这些都是能用的,对于我们的CSS来说也不会有例外的。</p>
<p>CSS(Cascading Style Sheets),到今天我也没有记得他的全称,CSS还有一个中文名字是层叠式样式表,事实上翻译成什么可能并不是我们关心的内容,我们需要关心的是他能做些什么。作为三剑客之一,它的主要目的在于可以让我们方便灵活地去控制Web页面的外观表现。我们可以用它做出像淘宝一样复杂的界面,也可以像我们的书本一样简单,不过如果要和我们书本一样简单的话,可能不需要用到CSS。HTML一开始就是依照报纸的格式而设计的,我们还可以继续用上面说到的编辑器,又或者是其他的。如果你喜欢DreamWeaver那也不错,不过一开始使用IDE可无助于我们写出良好的代码。</p>
<p>忘说了,CSS也是有版本的,和windows,Linux内核等等一样,但是更新可能没有那么频繁,HTML也是有版本的,JS也是有版本的,复杂的东西不是当前考虑的内容。</p>
<h2 id="代码结构"><span class="header-section-number">4.3</span> 代码结构</h2>
<p>对于我们的上面的Red示例来说,如果没有一个好的结构,那么以后可能就是这样子。</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="dt"><!DOCTYPE </span>html<span class="dt">></span>
<span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"></head></span>
<span class="kw"><body></span>
<span class="kw"><p</span><span class="ot"> style=</span><span class="st">"font-size: 22px;color:#f00;text-align: center;padding-left: 20px;"</span><span class="kw">></span>如果没有一个好的结构<span class="kw"></p></span>
<span class="kw"><p</span><span class="ot"> style=</span><span class="st">" font-size:44px;color:#3ed;text-indent: 2em;padding-left: 2em;"</span><span class="kw">></span>那么以后可能就是这样子。。。。<span class="kw"></p></span>
<span class="kw"></body></span>
<span class="kw"></html></span></code></pre></div>
<p>虽然我们看到的还是一样的:</p>
<div class="figure">
<img src="./images/nostyle.png" alt="No Style" />
<p class="caption">No Style</p>
</div>
<p>于是我们就按各种书上的建议重新写了上面的代码</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="dt"><!DOCTYPE </span>html<span class="dt">></span>
<span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"><title></span>CSS example<span class="kw"></title></span>
<span class="kw"><style</span><span class="ot"> type=</span><span class="st">"text/css"</span><span class="kw">></span>
<span class="fl">.para</span><span class="kw">{</span>
<span class="kw">font-size:</span> <span class="dt">22px</span><span class="kw">;</span>
<span class="kw">color:</span><span class="dt">#f00</span><span class="kw">;</span>
<span class="kw">text-align:</span> <span class="dt">center</span><span class="kw">;</span>
<span class="kw">padding-left:</span> <span class="dt">20px</span><span class="kw">;</span>
<span class="kw">}</span>
<span class="fl">.para2</span><span class="kw">{</span>
<span class="kw">font-size:</span><span class="dt">44px</span><span class="kw">;</span>
<span class="kw">color:</span><span class="dt">#3ed</span><span class="kw">;</span>
<span class="kw">text-indent:</span> <span class="dt">2em</span><span class="kw">;</span>
<span class="kw">padding-left:</span> <span class="dt">2em</span><span class="kw">;</span>
<span class="kw">}</span>
<span class="kw"></style></span>
<span class="kw"></head></span>
<span class="kw"><body></span>
<span class="kw"><p</span><span class="ot"> class=</span><span class="st">"para"</span><span class="kw">></span>如果没有一个好的结构<span class="kw"></p></span>
<span class="kw"><p</span><span class="ot"> class=</span><span class="st">"para2"</span><span class="kw">></span>那么以后可能就是这样子。。。。<span class="kw"></p></span>
<span class="kw"></body></span>
<span class="kw"></html></span></code></pre></div>
<p>总算比上面好看也好理解多了,这只是临时的用法,当文件太大的时候,正式一点的写法应该如下所示:</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="dt"><!DOCTYPE </span>html<span class="dt">></span>
<span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"><title></span>CSS example<span class="kw"></title></span>
<span class="kw"><style</span><span class="ot"> type=</span><span class="st">"text/css"</span><span class="ot"> href=</span><span class="st">"style.css"</span><span class="kw">></style></span>
<span class="kw"></head></span>
<span class="kw"><body></span>
<span class="kw"><p</span><span class="ot"> class=</span><span class="st">"para"</span><span class="kw">></span>如果没有一个好的结构<span class="kw"></p></span>
<span class="kw"><p</span><span class="ot"> class=</span><span class="st">"para2"</span><span class="kw">></span>那么以后可能就是这样子。。。。<span class="kw"></p></span>
<span class="kw"></body></span>
<span class="kw"></html></span></code></pre></div>
<p>我们需要</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="dt"><!DOCTYPE </span>html<span class="dt">></span>
<span class="kw"><html></span>
<span class="kw"><head></span>
<span class="kw"><title></span>CSS example<span class="kw"></title></span>
<span class="kw"><link</span><span class="ot"> href=</span><span class="st">"./style.css"</span><span class="ot"> rel=</span><span class="st">"stylesheet"</span><span class="ot"> type=</span><span class="st">"text/css"</span> <span class="kw">/></span>
<span class="kw"></head></span>
<span class="kw"><body></span>
<span class="kw"><p</span><span class="ot"> class=</span><span class="st">"para"</span><span class="kw">></span>如果没有一个好的结构<span class="kw"></p></span>
<span class="kw"><p</span><span class="ot"> class=</span><span class="st">"para2"</span><span class="kw">></span>那么以后可能就是这样子。。。。<span class="kw"></p></span>
<span class="kw"></body></span>
<span class="kw"></html></span></code></pre></div>
<p>然后我们有一个像app.js一样的style.css放在同目录下,而他的内容便是</p>
<div class="sourceCode"><pre class="sourceCode css"><code class="sourceCode css"><span class="fl">.para</span><span class="kw">{</span>
<span class="kw">font-size:</span> <span class="dt">22px</span><span class="kw">;</span>
<span class="kw">color:</span><span class="dt">#f00</span><span class="kw">;</span>
<span class="kw">text-align:</span> <span class="dt">center</span><span class="kw">;</span>
<span class="kw">padding-left:</span> <span class="dt">20px</span><span class="kw">;</span>
<span class="kw">}</span>
<span class="fl">.para2</span><span class="kw">{</span>
<span class="kw">font-size:</span><span class="dt">44px</span><span class="kw">;</span>
<span class="kw">color:</span><span class="dt">#3ed</span><span class="kw">;</span>
<span class="kw">text-indent:</span> <span class="dt">2em</span><span class="kw">;</span>
<span class="kw">padding-left:</span> <span class="dt">2em</span><span class="kw">;</span>
<span class="kw">}</span></code></pre></div>
<p>这代码和JS的代码有如此多的相似</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">var</span> para<span class="op">={</span>
<span class="dt">font_size</span><span class="op">:</span><span class="st">'22px'</span><span class="op">,</span>
<span class="dt">color</span><span class="op">:</span><span class="st">'#f00'</span><span class="op">,</span>
<span class="dt">text_align</span><span class="op">:</span><span class="st">'center'</span><span class="op">,</span>
<span class="dt">padding_left</span><span class="op">:</span><span class="st">'20px'</span><span class="op">,</span>
<span class="op">}</span></code></pre></div>
<p>而22px、20px以及#f00都是数值,因此:</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">var</span> para<span class="op">={</span>
<span class="dt">font_size</span><span class="op">:</span>22px<span class="op">,</span>
<span class="dt">color</span><span class="op">:</span>#f00<span class="op">,</span>
<span class="dt">text_align</span><span class="op">:</span>center<span class="op">,</span>
<span class="dt">padding_left</span><span class="op">:</span>20px<span class="op">,</span>
<span class="op">}</span> </code></pre></div>
<p>目测差距已经尽可能的小了,至于这些话题会在以后讨论到,如果要让我们的编译器更正确的工作,那么我们就需要非常多这样的符号,除非你乐意去理解:</p>
<div class="sourceCode"><pre class="sourceCode lisp"><code class="sourceCode commonlisp">(<span class="kw">dotimes</span> (i <span class="dv">4</span>) (<span class="kw">print</span> i))</code></pre></div>
<p>总的来说我们减少了符号的使用,但是用lisp便带入了更多的括号,不过这是一种简洁的表达方式,也许我们可以在其他语言中看到。</p>
<pre class="regex"><code>\d{2}/[A-Z][a-z][a-z]/\d{4}</code></pre>
<p>上面的代码,是为了从一堆数据中找出“某日/某月/某年”。如果一开始不理解那是正则表达式,就会觉得那个很复杂。</p>
<p>这门语言可能是为设计师而设计的,但是设计师大部分还是不懂编程的,不过相对来说这门语言还是比其他语言简单易懂一些。</p>
<h2 id="样式与目标"><span class="header-section-number">4.4</span> 样式与目标</h2>
<p>如下所示,就是我们的样式</p>
<div class="sourceCode"><pre class="sourceCode css"><code class="sourceCode css"><span class="fl">.para</span><span class="kw">{</span>
<span class="kw">font-size:</span> <span class="dt">22px</span><span class="kw">;</span>
<span class="kw">color:</span><span class="dt">#f00</span><span class="kw">;</span>
<span class="kw">text-align:</span> <span class="dt">center</span><span class="kw">;</span>
<span class="kw">padding-left:</span> <span class="dt">20px</span><span class="kw">;</span>
<span class="kw">}</span></code></pre></div>
<p>我们的目标就是</p>
<pre><code>如果没有一个好的结构</code></pre>
<p>所以样式和目标在这里牵手了,问题是他们是如何在一起的呢?下面就是CSS与HTML沟通的重点所在了:</p>
<h3 id="选择器"><span class="header-section-number">4.4.1</span> 选择器</h3>
<p>我们用到的选择器叫做类选择器,也就是class,或者说应该称之为class选择器更合适。与类选择器最常一起出现的是ID选择器,不过这个适用于比较高级的场合,诸如用JS控制DOM的时候就需要用到ID选择器。而基本的选择器就是如下面的例子:</p>
<pre><code>p.para{
color:#f0f;
}</code></pre>
<p>将代码添加到style.css的最下面会发现“如果没有一个好的结构”变成了粉红色,当然我们还会有这样的写法</p>
<pre><code>p>.para{
color:#f0f;
}</code></pre>
<p>为了产生上面的特殊的样式,虽然不好看,但是我们终于理解什么叫层叠样式了,下面的代码的重要度比上面高,也因此有更高的优先规则。</p>
<p>而通常我们可以通过一个</p>
<pre><code>p{
text-align:left;
}</code></pre>
<p>这样的元素选择器来给予所有的p元素一个左对齐。</p>
<p>还有复杂一点的复合型选择器,下面的是HTML文件</p>
<pre><code><!DOCTYPE html>
<html>
<head>
<title>CSS example</title>
<link href="./style.css" rel="stylesheet" type="text/css" />
</head>
<body>
<p class="para">如果没有一个好的结构</p>
<div id="content">
<p class="para2">那么以后可能就是这样子。。。。</p>
</div>
</body>
</html></code></pre>
<p>还有CSS文件</p>
<pre><code>.para{
font-size: 22px;
color:#f00;
text-align: center;
padding-left: 20px;
}
.para2{
font-size:44px;
color:#3ed;
text-indent: 2em;
padding-left: 2em;
}
p.para{
color:#f0f;
}
div#content p {
font-size:22px;
}</code></pre>
<h2 id="更有趣的css"><span class="header-section-number">4.5</span> 更有趣的CSS</h2>
<p>一个包含了para2以及para_bg的例子</p>
<pre><code> <div id="content">
<p class="para2 para_bg">那么以后可能就是这样子。。。。</p>
</div>
</code></pre>
<p>我们只是添加了一个黑色的背景</p>
<pre><code>.para_bg{
background-color:#000;
}</code></pre>
<p>重新改变后的网页变得比原来有趣了很多,所谓的继承与合并就是上面的例子。</p>
<p>我们还可以用CSS3做出更多有趣的效果,而这些并不在我们的讨论范围里面,因为我们讨论的是be a geek。</p>
<p>或许我们写的代码都是那么的简单,从HTML到Javascript,还有现在的CSS,只是总有一些核心的东西,而不是去考虑那些基础语法,基础的东西我们可以在实践的过程中一一发现。但是我们可能发现不了,或者在平时的使用中考虑不到一些有趣的用法或者说特殊的用法,这时候可以通过观察一些精致设计的代码中学习到。复杂的东西可以变得很简单,简单的东西也可以变得很复杂。</p>
<h1 id="无处不在的三剑客"><span class="header-section-number">5</span> 无处不在的三剑客</h1>
<p>这时我们终于了解了我们的三剑客,他们也就这么可以结合到一起了,HTML+Javascript+CSS是这一切的基础。而我们用到的其他语言如PHP、Python、Ruby等等到最后都会变成上面的结果,当然还有Coffeescript之类的语言都是以此为基础,这才是我们需要的知识。</p>
<h2 id="hellogeek"><span class="header-section-number">5.1</span> Hello,Geek</h2>
<p>有了一些些基础之后,我们终于能试着去写一些程序了。也是时候去创建一个像样的东西,或许你在一些界面设计方面的书籍看过类似的东西,可能我写得也没有那些内容好,只是这些都是一些过程。过去我们都是一点点慢慢过来的,只是现在我们也是如此,技术上的一些东西,事实上大家都是知道的。就好比我们都觉得我们可以开个超市,但是如果让我们去开超市的话,我们并不一定能赚钱。</p>
<p>学习编程的目的可能不在于我们能找到一份工作,那只是在编程之外的东西,虽然确实也是很确定的。但是除此之处,有些东西也是很重要的。</p>
<p>过去总是不理解为什么会一些人会不厌其烦地去回答别人的问题,有时候可能会想是一种能力越大责任越大的感觉,但是有时候在写一些博客或者回答别人的问题的时候我们又重新思考了这些问题,又重新学习了这些技能。所以这里可能说的不是关于编程的东西而是一些编程以外的东西,关于学习或者学习以外的东西。</p>
<h2 id="从源码学习"><span class="header-section-number">5.2</span> 从源码学习</h2>
<p>过去总觉得学了一种语言的语法便算是学会了一种语言,直到有一天接触运用该语言的项目的时候,虽然也会写上几行代码,但是却不像这种语言的风格。于是这也是这一篇的意义所在了:</p>
<h2 id="浏览器渲染过程"><span class="header-section-number">5.3</span> 浏览器渲染过程</h2>
<p>基本的渲染引擎的过程如下图所示:</p>
<div class="figure">
<img src="./images/flow.png" alt="flow" />
<p class="caption">flow</p>
</div>
<ul>
<li>解析HTML去构建DOM树</li>
<li>渲染树形结构</li>
<li>生成渲染的树形图布局</li>
<li>绘制树形图</li>
</ul>
<p>对于Webkit浏览器来说,他的过程如下所示:</p>
<div class="figure">
<img src="./images/webkitflow.png" alt="webkitflow" />
<p class="caption">webkitflow</p>
</div>
<h3 id="html"><span class="header-section-number">5.3.1</span> HTML</h3>
<p>写好HTML的一个要点在于读别人写的代码,这只是一方面,我们所说的HTML方面的内容可能不够多,原因有很多,很多东西都需要在实战中去解决。读万卷书和行万里路,分不清哪个有重要的意义,但是如果可以同时做好两个的话,成长会更快的。</p>
<p>写好HTML应该会有下面的要点</p>
<ul>
<li>了解标准及遵守绝大多数标准</li>
<li>注重可读性,从ID及CLASS的命名</li>
<li>关注SEO与代码的联系</li>
</ul>
<p>或许在这方面我也算不上很了解,不过按笔者的经验来说,大致就是如此。</p>
<p>多数情况下我们的HTML是类似于下面这样子的</p>
<div class="sourceCode"><pre class="sourceCode html"><code class="sourceCode html"><span class="kw"><div</span><span class="ot"> class=</span><span class="st">"col-md-3 right"</span><span class="kw">></span>
{% nevercache %}
{% include "includes/user_panel.html" %}
{% endnevercache %}
<span class="kw"><div</span><span class="ot"> class=</span><span class="st">"panel panel-default"</span><span class="kw">></span>
<span class="kw"><div</span><span class="ot"> class=</span><span class="st">"panel-body"</span><span class="kw">></span>
{% block right_panel %}
{% ifinstalled mezzanine.twitter %}
{% include "twitter/tweets.html" %}
{% endifinstalled %}
{% endblock %}
<span class="kw"></div></span>
<span class="kw"></div></span>
<span class="kw"></div></span></code></pre></div>
<p>换句话说HTML只是基础,而不是日常用到的。我们的HTML是由template生成的,我们可以借助于mustache.js又或者是angluarjs之类的js库来生成最后的HTML,所以这里只是一个开始。</p>
<p>还需要了解的一部分就是HTML的另外一个重要的部分,DOM树形结构</p>
<h2 id="dom树形结构图"><span class="header-section-number">5.4</span> DOM树形结构图</h2>
<blockquote>
<p>DOM是文档对象化模型(Document Object Model)的简称。DOM Tree是指通过DOM将HTML页面进行解析,并生成的HTML tree树状结构和对应访问方法。</p>
</blockquote>
<div class="figure">
<img src="./images/dom_tree.jpg" alt="DOM Tree" />
<p class="caption">DOM Tree</p>
</div>
<h3 id="javascript"><span class="header-section-number">5.4.1</span> javascript</h3>
<p>这里以未压缩的jQuery源码和zepto.js作一个小小的比较,zepto.js是兼容jQuery的,因此我们举几个有意思的函数作一简单的比较,关于源码可以在官网上下载到。</p>
<p>在zepto.js下面判断一个值是否是函数的方面如下,</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript"><span class="kw">function</span> <span class="at">isFunction</span>(value) <span class="op">{</span> <span class="cf">return</span> <span class="at">type</span>(value) <span class="op">==</span> <span class="st">"function"</span> <span class="op">}</span></code></pre></div>
<p>而在jQuery下面则是这样的</p>
<div class="sourceCode"><pre class="sourceCode javascript"><code class="sourceCode javascript">isFunction<span class="op">:</span> <span class="kw">function</span>( obj ) <span class="op">{</span>
<span class="cf">return</span> <span class="va">jQuery</span>.<span class="at">type</span>(obj) <span class="op">===</span> <span class="st">"function"</span><span class="op">;</span>