中英文字符的映射(TRANSLATE函数的运用)
又有很長(zhǎng)時(shí)間沒(méi)有更新博客了=。=
這次想簡(jiǎn)單介紹一下最近的數(shù)據(jù)清洗的工作中的發(fā)現(xiàn)的一些小方法,因?yàn)樵诰W(wǎng)上搜了一下,并沒(méi)發(fā)現(xiàn)有人總結(jié)過(guò)。
背景
最近處理的數(shù)據(jù)是多個(gè)不同部門的人工錄入的數(shù)據(jù),莫名其妙的問(wèn)題非常多。
其中一個(gè)就是中英文符號(hào)的問(wèn)題,我發(fā)現(xiàn)大部分的中英文符號(hào)存在以下關(guān)系(代碼是Python代碼)
65281 ! => 33 !
65282 " => 34 "
65283 # => 35 #
65284 $ => 36 $
65285 % => 37 %
…省略…
65368 x => 120 x
65369 y => 121 y
65370 z => 122 z
65371 { => 123 {
65372 | => 124 |
65373 } => 125 }
65374 ~ => 126 ~
65375 ⦅ => 127
65376 ⦆ => 128 €
65377 。 => 129 ?
65378 「 => 130 ?
65379 」 => 131 ?
65380 、 => 132 ?
有幾個(gè)字符還顯示不出來(lái)=。=
需要注意的是,最后幾行例子并不是對(duì)應(yīng)的。但是句號(hào)和頓號(hào)我感覺(jué)還是列出來(lái)比較好。
以前我都是使用的replace來(lái)做,現(xiàn)在看來(lái)非常的扯淡,代碼完全沒(méi)有任何美感了。
Python中的解決方法
因?yàn)樯婕暗降姆?hào)比較多,在我這邊舉例就就說(shuō)一下有關(guān)函數(shù)了。
具體要轉(zhuǎn)變哪些符號(hào),大家根據(jù)自己的需求來(lái)吧。
ps:我剛學(xué)Python的時(shí)候,根本沒(méi)有多去關(guān)注translate函數(shù),感覺(jué)用法很蠢,如今真香!
ps:值得一提的是,我看了好久其他大佬的案例,才發(fā)現(xiàn)代碼里的這個(gè)str.maketrans中的str就是Python里的基礎(chǔ)類str。
我總以為是其他庫(kù)(例如string庫(kù))被重命名為str了。
Oracle中的解決方法
CREATE OR REPLACE FUNCTION STANDARDIZE_STR(TEXT0 IN VARCHAR2) RETURN VARCHAR2 ASres VARCHAR2; BEGINres := TEXT0;res := TRANSLATE(res, 'Dyson!@#$%', 'Dyson'); --見(jiàn)代碼后的“注”res := TRANSLATE(res, '123', 'abc'); RETURN res; END;由于涉及的符號(hào)替換可能會(huì)比較多,所以我就寫在了ORACLE函數(shù)中,再到SQL查詢里調(diào)用。
由于我原來(lái)的代碼我暫時(shí)沒(méi)法復(fù)制出來(lái)(安全管理嚴(yán)格),所以我這部分代碼沒(méi)有運(yùn)行過(guò),敲錯(cuò)的話還請(qǐng)見(jiàn)諒。
注:
此處有點(diǎn)微妙,在Oralce中,是可以用TRANSLATE函數(shù)來(lái)刪除特定的一些字符的。但是用法有點(diǎn)奇怪,不知道是不是我沒(méi)有g(shù)et到正確方式。
理論上,當(dāng)TRANSLATE的第二個(gè)參數(shù)的長(zhǎng)度應(yīng)該與第三個(gè)參數(shù)的長(zhǎng)度一樣的,這樣才能一一對(duì)應(yīng)。但是在Oracle中,第二個(gè)參數(shù)的長(zhǎng)度是允許大于第三個(gè)參數(shù)的長(zhǎng)度的,多出來(lái)的部分,視為需要?jiǎng)h除的部分=。=
所以我這行代碼的意思,其實(shí)是為了刪除“!@#$%”這些符號(hào)。
MySQL中的解決方法
#創(chuàng)建前刪除已經(jīng)創(chuàng)建的自定義函數(shù) DROP FUNCTION IF EXISTS translate_str; #創(chuàng)建函數(shù) DELIMITER $$ CREATE FUNCTION `translate_str`(str0 LONGTEXT,from_str VARCHAR(1000),to_str VARCHAR(1000)) RETURNS LONGTEXTDETERMINISTIC BEGIN DECLARE i0 INT;DECLARE f_str VARCHAR(1000);DECLARE t_str VARCHAR(1000);# 本函數(shù)是在仿制oracle的translate函數(shù)# 具體函數(shù)用法參考https://blog.csdn.net/weixin_39461443/article/details/102684234# 若from_str沒(méi)有to_str長(zhǎng),那么to_str超長(zhǎng)的部分將會(huì)被忽略# 若from_str比to_str長(zhǎng),那么from_str超長(zhǎng)的部分將視為需要被刪除的字符SET i0 = 1;# 循環(huán)查找以替換所有的目標(biāo)字符串WHILE i0 <= CHAR_LENGTH(from_str) DOSET f_str = SUBSTR(from_str, i0, 1);SET t_str = SUBSTR(to_str, i0, 1);# 若存在from_str更長(zhǎng)的情況,超長(zhǎng)部分將被替換為空字符串IF t_str IS NULL THENSET t_str = '';END IF;# 替換對(duì)應(yīng)的字符串IF INSTR(str0, f_str) > 0 THENSET str0 = REPLACE(str0, f_str, t_str);END IF; -- SET i0 = i0 + 1;END WHILE; RETURN str0; END$$ DELIMITER ;總結(jié)
以上是生活随笔為你收集整理的中英文字符的映射(TRANSLATE函数的运用)的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 【马三北漂记】之终章
- 下一篇: UEFI Protocol使用