1、密碼學
起源:古代戰爭
古代打仗的時候,會要信使騎個馬送信,他們經常會擔心信使被抓,
移位式加密:密碼棒
比較早的一種加密方式

一個布條纏在密碼棒上面,兩邊都有同一規格的密碼棒
替換式加密

也可以用碼表
2.現代密碼學
不止可以用于文字內容,還可以用于各種二進制資料,
對稱加密:
跟替換式加密很像
原理:
使用密鑰和加密演算法對資料進行轉換,得到的無意義資料即為密文;使用密鑰和解密演算法對密文進行逆向轉換,得到原資料,
程序:
原資料,用加密演算法以及密鑰,把他改成了看不懂的密文,這個時候對方拿到密文,并且他有密鑰,我有密鑰,其他任何人都沒有,然后他就可以去解密,他使用解密演算法配合上密鑰,他就能解密,得到原資料,其他任何人拿到這個資料是沒有用的,

這個對計算機很有用,為什么?因為我們通訊的時候,我們的網路是完全不可信的,從我家到你家這一路上,可能有非常非常多的中間節點,他們想拿我們的中間的資料輕而易舉,為什么?我們網路傳資料,比如說我給你發一條資訊,不是這個資訊在一條路上走,而是喊話式的,都是輻射式的,
他跟傳統的替換式加密有什么不同呢?他可以加密二進制檔案
經典演算法:
DES(由于密鑰太短而被棄用了),AES
為什么密鑰短就被棄用?因為密鑰短就可能會被破解,
什么叫破解呢?什么叫對稱加密的密鑰的破解呢?就是這樣的,我們通訊的破解,我們古代戰爭寫信,我知道你的密碼棒是什么規格,我知道你的碼表是什么,當我拿到你加密后的那一封密文,我可以給你恢復回來,那么我拿到你這個密文或碼表,就破解了,他的關鍵是什么呢?你能夠拿到一組原文和密文的對,然后你用你準備好的密鑰對這個密文解密之后,他真的恢復成原文了,這表示破解成功了,
同樣,有破解就有反破解,反破解的思路非常直,就是我讓你破解的方法更加復雜,最優秀的加密演算法就是,他的密鑰的破解方式只能是窮舉法,你不可能讓別人破解不了,只是成本非常高,比如要一千年,一萬年才能破解,那么我認為你這個東西不能破解,
非對稱加密:
原理:
使用公鑰對資料進行加密得到密文;使用私鑰對資料進行解密得到元資料,
延伸用途:數字簽名
經典演算法:
RSA(加密解密,簽名驗證都可以)、DSA(專門設計用來簽名的,簽名和驗證的程序特別快,有速度優勢,橢圓曲線全稱就叫ECDSA)

怎么做到的呢?用的是數學知識,我可以簡單解釋一下,但是我的這個解釋是不足以完全說明非對稱加密的,因為非對稱加密最簡單的演算法也比較復雜,RSA演算法就算一種比較簡單的演算法了,但是還是比較不好理解,所以我跟你舉一個簡單例子,這個例子可能會有漏洞,但是你要知道她是什么意思,
比如,我們雙方通訊了,我們規定通訊內容只有十個,0-9,只能發這十個,比如我現在給你發一個訊息110,但是我如果被人截獲了那我就完蛋了,所以我要對她做一下轉換,然后我要怎么轉?我的演算法是什么?我的加密密鑰和解密密鑰是什么?這個時候就體現出來了他的用處了,我的加密演算法是,對我的每一個字符都做一個加法,而這個加法具體加幾,就是我的密鑰了,那么我規定,我的加密密鑰是4,我的解密密鑰是6,加密:110–>554,發出去,接下來, 我要解密,我的解密演算法還是加,但是加的是6,554–>110,恢復了,
這個例子雖然有漏洞,但是她能解釋非對稱加密的原理,他是跟溢位有關的,如果不可以溢位的話,非對稱加密就沒法玩了,你各種溢位,刪掉他前面的點,這個是非對稱加密很關鍵的一個點,

現在,我假設我們路上有壞人,他們會看到我們的訊息,但是現在,我們可以做加密了,而且,我可以把密鑰,就這樣在網上扔給對方,這個扔本身,他也是危險的,對稱加密,不是挺安全的嗎?為什么又要非對稱加密呢?有一個很重要的原因,就是你的密鑰怎么給對方,他是一個難題,這可不是你要來我家,天天來我家,我給你配一把鑰匙,見面的時候我把鑰匙給你就可以了,不是這樣的,而是我要把鑰匙寄給你,如果你家的鑰匙真的那么受人關注,并且快遞員他們都會拆開看一看的話,你敢把鑰匙寄給別人嗎?不敢吧,網上的這種通訊也是一樣,你們兩個通過對稱加密來做通訊是完全沒問題的,可是你怎么把密鑰給對方呢?這個問題非常難解決,而且各種各樣的情形,有很多是,我們兩個臨時起意,想聊天了,加個好友吧,怎么加?我跑你家把密鑰給你呀?是吧?這就是非對稱加密他很重要的一個好處了,我可以在網上直接把密鑰進行傳輸,沒有任何安全隱患,
看一下怎么沒有安全隱患,首先,我把我的加密密鑰從a給到b,b也把她的加密密鑰從b給到a,首先我看a和b能不能通訊,比如a要給b發訊息,我用b的加密密鑰,去加密我的原資料,加密完以后就是密文了,b拿解密密鑰解密,就得到原資料,同樣,b給a發訊息也是這樣,
那我們假設c拿到這個密文他肯定看不懂,但是如果他不僅僅拿到密文,他還拿到了我們傳輸程序中發送的這個兩個加密密鑰,現在他能看我們的密文嗎?還是不能看的,假如我說可以看,你想想,我怎么看?我現在有一個密文,是a發給b的,他用b的加密密鑰加密了, 你說c拿哪個密鑰來解?都不行,非對稱加密很關鍵的一個點是,他加密和解密用的不是一個密鑰,所以這個時候你拿我的兩個加密密鑰是沒有用的,解密密鑰是要拿在手里不能動的,這個是關鍵,一定要拿在手里面,誰都不能給,不可能往外發送的,而加密密鑰隨便往外公開,事實上你往外公開的這個加密密鑰他叫公鑰,解密密鑰叫私鑰,

非對稱加密延伸用途:數字簽名
公鑰能不能解私鑰?
首先有一個問題,私鑰是可以解公鑰的,那么公鑰可不可以解私鑰呢?是可以的,
但是有一點要注意,公鑰和私鑰是不能反的,因為很多時候公鑰是可以被計算出來的,有一種非對稱加密演算法叫橢圓曲線演算法,他是位元幣用的一種演算法,他的公鑰就是依靠私鑰算出來的,你拿到私鑰就相當于公鑰和私鑰同時拿在手里,雖然他們在資料轉化上有對等關系,但是很多時候你的公鑰是可以被人算出來的,所以你公布一個公鑰出去沒關系,本來就要公開,只要私鑰不公開你沒發推算出我的私鑰,
還有一種情況就是RSA,RSA他的公鑰甚至只有一個,你家公鑰是這個值,我家公鑰也是這個值,也不是公鑰完全是一個值,就是公鑰的一部分,公鑰最關鍵的那一部分是一樣的,好像是65537我記得,所以公鑰和私鑰是不能對換的,但是他們在加密上是完全一樣的,你可以解我,我可以解你,
由于有這么一種特性,我就可以去做簽名和驗證了,
簽名和認證:
現在有一種比較常見的用法就是在網上進行數字簽名,進行電子簽名,就是我有一個我的密鑰,我對我的資料,比如說我聲稱我欠了小莊一百塊錢,我可以手寫,我也可以使用電子簽名式,他是怎么簽名呢?就是使用我的某個密鑰,對我寫的文章進行加密演算法轉化之后,別人拿到之后,再用另外的公鑰解密,一看,可以置換成原資料,就可以證明這個東西確實是我寫的,

另外,還會有這樣一步,你只拿著這個簽名資料很不方便,每次看都要用公鑰解密以后才能看到原資料,所以一般會把原資料和簽名資料一起發送出來,這個時候你看原資料可以看,你要驗證這個資料可以用簽名資料還原,

3.Base64
將二進制資料轉換成由64個字符組成的字串的編碼演算法,(a-z、A-Z、0-9、+、/)
什么是二進制資料?非文本資料就是二進制資料,廣義的,所有的計算機資料都是二進制資料,因為電信號只有1010,計算機資料只有兩個位,計算機資料都是二進制資料,不管什么文本檔案啊,電影啊,word檔案啊,圖片這些都是二進制資料,而其中有一種比較特殊的叫做文本資料,就是純文字,比如字串,比如你的一個txt檔案里面存的一些文字,這些叫文本資料或者叫字符資料,文本資料之外的,就是我們通常溝通的時候所說的二進制資料,也就是狹義的二進制資料,所以資料就分兩種,文本資料和二進制資料,
base64的碼表:

2的6次方是64,base64是6位的
他是怎么轉換的呢?他是將你的資料切一下,我們做資料的時候不是一個位元組有8位嗎?一位是0或者1,只能二選一,八位是一個位元組,但是base64為了能讓你的資料變成字串,他就把你切成了6位放在一起,具體的轉化是這樣的,Man轉化成base64就是TWFu,

base64轉化完以后會把資料量變大的,
怎么讓你的資料base轉化以后還不增大呢?
那就別用base64,用base256,但是為什么base64被創建出來?就是因為那些常見字符沒有256個,如果真有256個那還需要什么base64,base64的目的是什么?他的目的就是把你的二進制資料(狹義的)轉化成文本資料,給轉化成字串,
用途:
讓原資料具有字串所具有的特性,如可以放在URL中傳輸、可以保存到文本檔案、可以通過普通聊天軟體進行文本傳輸,(把非字串轉成字串)
把原本人眼可以讀懂的字串變成讀不懂的字串,降低偷窺風險,
什么時候會需要base64呢?舉一個比較早期的場景,就是郵箱剛被發明,郵箱不能發圖片的,但是電腦可以存圖片,那么我怎么給你發圖片呢?好,我用base64轉一下,檔案變大了,沒關系啊,慢慢傳,然后再用base64的解碼演算法給他解出來,那么我們就通過文本的方式傳圖片,再舉一個例,假如我們兩個造了一個新的聊天軟體,但是咱倆技術有限,沒法支持圖片,傳不了圖片,怎么辦?沒關系,把圖片轉成base64,然后我給你傳base64的文本資料,傳過去之后你再在本地解一下,解碼完就是那個圖片了,這個就是什么呢?就是有的時候他有限制,不能這么做,古老的郵箱就是這樣,沒這個功能,不能傳圖片,我又想傳圖片,好,我就用base64轉一下,
base64加密傳輸圖片,可以更安全和高效嗎?不是的,安全只能靠加密,base64不是加密;高效,base64轉化后資料變大了,變長了1/3,那還能高效嗎?你不管是存盤還是傳輸,還是讀取,他的速度都變慢了,而且還占你帶寬,你可能本來傳這個東西,這個東西傳完以后,傳別的東西,可以更早傳完,但是由于你這東西被base64轉過一遍,完蛋了,你需要延長1/3的傳輸時間,base64絕對沒有什么高效,相反他是低效的,能不base64一定不要base64,而且這個東西有毒,你每次做這個東西他都會變長,
Base58
base64有一個變種,base58,他去掉了0和大寫o,英文的大寫i和小寫l,另外還有兩個+和/,他用在位元幣或者其他虛擬幣的地址上面,這個地址有什么特點呢?他可能會被手抄,去掉+和/是為了方便雙擊復制,
4.URL encoding
url地址的編碼是base64 的另一個變種
url的編碼也是base64的,但是他有一點點區別:
將url中的保留字符使用百分號“%”進行編碼
舉例:將保留字符中的&轉化成%26:

目的:消除歧義,避免錯誤
還有就是用于中文顯示

顯示是有中文的,但是復制下來就沒了
https://www.google.com/search?q=%E6%A4%AD%E5%9C%86%E6%9B%B2%E7%BA%BF%E7%AE%97%E6%B3%95&oq=%E6%A4%AD%E5%9C%86%E6%9B%B2%E7%BA%BF%E7%AE%97%E6%B3%95&aqs=chrome..69i57j0l2.7739j0j7&sourceid=chrome&ie=UTF-8
5.壓縮和解壓縮
壓縮:把資料換一種方式存盤,以減小存盤空間
解壓縮:把壓縮后的資料還原成原先的形式,以便使用
常見的壓縮演算法:DEFLATE(zip用的壓縮演算法)、JPEG、MP3
壓縮屬于編碼嗎?
編碼到底是什么?把a格式轉化成b格式,同時b格式是可以轉回來的,不會損失任何資訊,不會增加任何資訊,壓縮也是屬于編碼的一種,
下面一節舉例詳說
6.媒體資料的編解碼
媒體資料是什么?就是圖片啊、視頻、音頻這些東西,他們的編解碼是什么呢?他們的編解碼就是把原先的資料轉化成可以存盤的一種編碼格式,比如對于圖片就是把影像資料編成檔案,
舉個栗子,影像怎么做編碼呢?
比如我有一個圖片,這個圖片是64x64的,他是一個純白的圖片,那么我怎么寫,怎么保存呢?他在記憶體里面可能是一個bitmap,當我要把他編碼出來,要保存的時候,怎么存?
ffffff表示一個白點
ffffffffffff…64x6個
ffffffffffff…64x6個
ffffffffffff…64x6個
…64行
這個就是編碼后的圖片,但是這樣好煩啊,這么大,我們可以壓縮,在編碼的同時進行壓縮,怎么壓縮呢?有各種各樣的壓縮方法,假如我們真的要做壓縮的話,DEFLATE演算法以及各種其他演算法他們本質上是什么呢?
舉例:aaaaaaaaaaaaaaaaa…aaaaaaaaaaaaaaaaaaabbbbbbbb…bbbbbb
某種粗略壓縮后:text:a=100;b=20
上面的圖片也可以:image:64*64;ffffff=[0,0]-[63,63]
同樣音頻視頻的壓縮也是這樣的,上面只是舉例,這個壓縮并不嚴謹,優秀的壓縮演算法永遠不會讓檔案變大,上面這種一旦種類變多,可能壓縮完后比檔案本體還大,
有損壓縮和無損壓縮:可以把她的像素變小一點,也可以把顏色數改少一點,這樣壓完我的資料就會有損失,
7.序列化
我java記憶體里面有一個資料,他有幾個屬性

這是在記憶體里面,我需要把這些東西傳出來,一個是我們的網路上,另外也可能是我們的手機或者本地存盤,但是我們的記憶體里面是亂亂的,我們怎么存各種格式?我要把他拿出來,成線性的,可以通用決議的一個格式,這就是序列化,
像上面的我可以序列化出來成json格式,如果序列化出來,我可以選擇json格式,json只是序列化的一個選項,你可以序列化成json、xml…總之你只要把她轉化成可以存盤,可以傳輸,她是一個線性的就可以了,

序列化:把資料物件(一般是記憶體中的,如JVM中的物件)轉化成位元組序列的程序
反序列化:把位元組序列重新轉換成記憶體中的物件,
目的:就是跟外界通訊
序列化屬于編碼嗎?
序列化嚴格來說不屬于編碼,因為序列化他的原型在記憶體里面,編碼是什么a格式變b格式,編碼是已經成型的兩個東西他的格式轉換,但是序列化他的原型就不是格式,是記憶體里面的一坨,只是嚴格意義上來說不是編碼,其實編碼并沒有一個嚴格規定,
8.Hash
定義:
把任意資料轉換成指定大小范圍的資料(通常很小)
比如我們有兩百個同學,我們把每一個學員編一個號,001,003…這個程序就是一個hash程序,而每個人他的編號就是一個hash值,
作用:
用作摘要、數字指紋
比如:
直接用字串的長度做hash
“haha”–>4
“pa”–>2
后面是數值就是hash值,這是一種很差勁的hash,因為
“hehe”–>4
hash他會有身份識別的這種要求,所以hash要求有極小的碰撞率,那么就研究你的hash演算法要怎么算,給你的資料可能非常大,也可能非常小,你都需要快速得出結果,并且互相之間不會碰撞,
經典演算法:
MD5(在防破解方面已經基本被遺棄了,因為他太容易破解了)、SHA1、SHA256
實際用途:
資料完整性驗證:
比如我們要下一個安裝包,那個發布者可能會在下面給你提供一個用于驗證的hash值,他會給你指明這是一個sha1值還是一個sha256,還是一個md5,他會跟你說,也有可能會給你提供多個驗證的值,這個有什么作用呢?上傳者這有一個源檔案,他有5個g,他的md5值算完以后是7788, 你下載以后,你這個下載檔案可能已經損壞了,可能下載程序中你的下載工具出錯了,或者有人修改你的網路了,總之你下完以后,這個東西可能是破壞了的,你對她也算一下你的hash值,比如算一下他的md5,如果也是7788,證明你下載的這個檔案他是完整的,如果你算完是2567,那么你這個檔案下載失敗了,hash就像是在你的一堆資料里面抽取特征值一樣,如果你多次計算都是這個結果,那么他就可以當成一個指紋一樣的存在,
(這一部分理解有問題得修改)
快速查找:
hashCode()和HashMap
java中有用到hash的時候,重寫equals方法的時候也要重寫hashCode方法

hashcode就是用來快速判斷是否對等的(預判斷)
隱私保護:
前幾年有一個網站,被脫褲了,技術的博客網站被脫褲了,被脫褲以后就有很多人說他們是用了明文存盤,所以才導致用戶的隱私被泄漏,這個是什么原因呢?首先,用戶資料被盜,很容易理解,如果是明文存盤,盜走的人將你的用戶名和密碼在別的網站不斷嘗試,就會導致很多用戶資訊被盜取,那么什么是非明文存盤呢?就是服務器收到用戶賬號和密碼以后,用md5轉化后存盤(下次登錄就把傳過來的密碼md5加密轉化一次以后再對照本地存盤的密碼),這樣被盜走以后,他也沒辦法去其他網站登錄,
同時,有個東西叫加鹽,什么叫加鹽呢?那些黑客也在進步,我們覺得哪里比較難破解呢?因為hash不可逆,一,你拿到這個東西不能直接在網站登錄驗證,因為在轉一次就是另外一個數值了;二,這個東西還沒法逆向算出他的原密碼,可是那些黑客時間多的是,他們把常用的密碼一個一個存起來再映射,當他們盜了你們的庫以后,逆推,比如密碼是123456,md5轉化后是ddddd,黑客們自己做一個md5映射表,就知道ddddd對應的原密碼是123456了,這個暴力破解的映射表就叫彩虹表,可以一定程度上破解這種使用hash存盤密碼的方式,那么,使用加鹽就可以破解這個東西,什么叫加鹽,每個網站自己定義一個鹽,這個鹽是你嚴格保密的,不會被別人拿走,脫褲的時候被人把鹽也拿走也挺慘的,鹽是什么呢?鹽就是你做md5或者sha1的時候,你不是用123456做hash,而是加個333,123456333,這個333就是你的鹽,他的md5值就完全是另外一個值了,每個網站的鹽都不一樣,這樣就導致彩虹表失效了,一般鹽都不會是333,而是一長串非常規字符,
Hash是編碼嗎?
不是,編碼是什么?你編過去,編回來任何資料都不損失,hash是什么?hash是抽取你的特征,他不能逆向,
Hash是加密嗎?據說MD5是不可逆加密?
不是加密,百度百科都搞錯了,他是一種不可逆的轉化,還有人發明一個不可逆加密,聽著很有道理,但是假如你就是要把這個詞他的意思改掉,加密的意思就是把A格式改成B格式,別人看不懂,并且可以被還原,但是你硬是要把加密這兩個字曲解成別的意思,他的意思是讓別人看不懂,那我承認MD5是一種不可逆加密,但是加密這個詞是有他自己的定義的,這個詞不能亂說的,
9.Hash與非對稱加密

這是之前一個圖,這個圖有個缺點,他的簽名資料和原資料是一樣大的,因為簽名資料可以還原回來呀,你檔案小沒關系,一個10G的視頻,他的簽名要10G那么大,想想就覺得好臃腫啊,事實上簽名的做法,他們會對資料先進行hash,再進行簽名,對那個hash值進行簽名,

10.字符集
含義:一個由整數向現實世界中的文字符號的Map
分支:
ASCII:
128個字符,一個位元組(可以使用256個,但是ASCII只用了其中128個)
ISO-8859-1:
對ASCII進行擴充,1 位元組
Unicode:
13萬字符,多位元組
UTF-8:Unicode編碼分支
UTF-16:Unicode編碼分支
什么叫編碼分支呢?
比如我有三個字:中國人
其中“中”他可能對應的是00000001,
“國”對應的是00001111,
“人”對應的是11111111
這是他們對應的編碼,但是實際表達的時候我們可能不會這么寫
中01
國001111
人11111111
短了一點,這個可能就是UTF-8
另外一種方法,也許是
中0001
國1111
人11111111
這種可能是UTF-16
就是他們的字符集可能一致,但是具體的編碼方式可能不一致,這個就是不同的編碼,當然上面這個例子是不對的,比如UTF-8和UTF-16有一個很明顯的區別,UTF-16是16位表示一個字符,所以不存在上面這么短的,上面只是在舉例子,
GBK
GBK/GBK2312/GBK18030:中國自研標準,多位元組,字符集+編碼
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/172022.html
標籤:其他
上一篇:Redis的雪崩,穿透,擊穿
