python寫文字方法_Transcrypt: 用Python寫js的方法

Transcrypt是一個很有意思的工具:

它讓你告別手寫繁復的JavaScript代碼,使用相對簡明清晰的Python代替這一工作。

之后使用這個工具,可以把Python編寫的代碼轉換成JavaScript。

1. 為什么不直接寫JavsScript?

JavaScript本身不算是很難的編程語言,但還是有很多不便之處。這里只能舉幾個例子:

1.1 js的模塊化問題。

想要實現一個很復雜的js程序,一般要考慮將不同的功能拆分成模塊,然后各自完成各自的任務。

然而,js本身沒有什么方式可以做到這一點:

要么在瀏覽器或者NodeJS中,使用require這樣的方案(”AMD”—-模塊異步加載)(瀏覽器還需要額外加載require.js),

要么使用各種打包工具(CommonJS—-規定了通用的模塊定義方式),根據模塊各部分代碼相互關系,將所有的代碼打包進一個巨大的文件。

Transcrypt支持Python的模塊機制(import語法),效果上最后還是生成一個打包的代碼文件,但使用起來,比CommonJS要清晰一些。

1.2 缺乏對class這樣的關鍵字的支持

JavaScript雖然算是一種基于對象的語言—-JavaScript中包括數字、字符串等都是對象,

但又沒有辦法通過class來自己聲明一個對象。

這就導致不同的程序員,會采用不同的方案來構建對象。比如有使用Object的:

var owl = {};

owl.color = "white";

owl.category = "Bubo bubo";

owl.eat = function(){ ... };

或者改寫一個函數,增加各種attributes:

function Owl(){

var self = this;

this.color = "white";

this.category = "Bubo bubo";

this.eat = function(){ ... };

return this;

}

var owl = new Owl();

1.3 缺乏語法糖,代碼復雜

Python簡潔的語法,很多得益于豐富的語法糖:

很簡潔的幾句話就可以實現復雜的功能,而JavaScript則可能要從頭開始寫一系列代碼。

舉幾個例子:

a) 使用給定的值生成一個字符串

output = """My name is {name}, I'm {age} years old.

My favourite fruit is {favourite}.""".format({

"favourite": "banana",

"name": "Alice",

"age": 18,

})

console.log(output)

這也是一個簡單的例子,如何套用模板,將數據轉換成供顯示的文本。js的解決方案就復雜許多:

首先,js是不支持帶有換行的字符串變量的。所以我們不能用Python"""..."""這種語法,指定一個帶有換行的字符串。

其次,也不能在js的字符串中定義占位符,然后用數據填充,所以要自行斷開字符串,將數據與字符串合并。

看起來結果就是:

var data = {

"favourite": "banana",

"name": "Alice",

"age": 18,

};

var output = "My name is" + data.name + ", I'm" + data.age + "years old.\n";

output += "My favourite fruit is" + data.favourite + ".";

console.log(output);

即使看上去代碼量差不多,這樣做還是有一個缺點:

如果需要修改模板,使用Python,只要將帶有占位符的字符串換掉就可以了(比如字符串在單獨的模板文件中予以定義),

但使用js,就需要具體修改帶有邏輯運算符的代碼。這樣就很不直觀,容易出錯。

b) 根據已有數據生成一個新的數組

假設我們有一個數組[-2, -1, 0, 1, 2, 3, 4],想列出這個數組中大于0的各個數字的平方。

使用js的思路,是新建一個數組,然后遍歷原數組,檢查各項是否大于0, 如果是,將結果記錄到新的數組:

var original = [-2, -1, 0, 1, 2, 3, 4];

var result = [];

for(var i=0; i

if(original[i] > 0){

result.push(Math.pow(original[i], 2));

}

}

Python則簡單很多。Python支持在構建list的時候,指定條件,并使用表達式指定要放入list的值:

original = [-2, -1, 0, 1, 2, 3, 4]

result = [each ** 2 for each in original if each > 0]

1.4 復雜的異步編程

JavaScript的另一個令人詬病的問題,是在調用一系列異步調用時難以組織代碼。

實際應用中,無論NodeJS還是瀏覽器,都要遇到各種異步調用的代碼。

假設我們有3個函數:

readFile用于讀取一個文件;

encrypt用于加密數據;

upload用于將數據上傳到服務器。

這三個函數都是異步調用的。

傳統的方式,一般是在實際完成功能需要的參數之外,這些函數還接受一個callback(回調函數)作為輸入。

這樣調用上述函數之后,他們會立刻返回,并不耽誤時間。然后當函數對應的后臺任務完成時,再呼叫callback,傳入結果。

比如這樣看,可以假設readFile的用法是readFile(filename, callback)。

這個函數接受一個filename作為要讀取的文件名,然后在讀取完畢時呼叫callback函數,傳入讀取結果。

實際調用時,要寫成:

readFile("/path/to/somefile", function(err, data){

if(err){

...

return; // 如果讀取文件出錯

}

// 否則讀取文件成功,繼續做下一步的事情

});

假如我們想在讀取文件后,將文件內容加密,就要在上述代碼的讀取成功處,

加上對encrypt=encrypt(data, callback)函數的調用。于是代碼就成了這個樣子:

readFile("/path/to/somefile", function(err, data){

if(err){

...

return; // 如果讀取文件出錯

}

// 讀取文件成功,加密data

encrypt(data, function(err, ciphertext){

if(err){

...

return; // 加密失敗

}

// 加密文件成功,繼續做別的事情

});

});

如果進一步,想在加密之后,將密文上傳到服務器,整個代碼就……

readFile("/path/to/somefile", function(err, data){

if(err){

...

return; // 如果讀取文件出錯

}

// 讀取文件成功,加密data

encrypt(data, function(err, ciphertext){

if(err){

...

return; // 加密失敗

}

// 加密文件成功,密文是ciphertext,將它上傳

upload(ciphertext, function(err, result){

if(err){

...

return; // 上傳失敗

}

// 上傳成功

});

});

});

很多時候,要完成的工作都是上面這樣一連串的。

js的回調機制,就很容易引入如上所示不斷嵌套的代碼,讓結果變得十分難看,所謂的回調地獄。

為了解決這個問題,JavaScript引入了Promise機制。

這樣每個函數就都返回一個Promise對象。

Promise對象支持使用.then()這樣的方法,將流程串聯起來:

readFile("/path/to/somefile")

.then(encrypt)

.then(upload)

.catch(function(err){

...

// 如果上面某一步出錯的話,就直接跳到這里

});

這樣簡明了許多。

Transcrypt在Promise機制的基礎上,結合了Python 3引入的async和await語法,讓上面的過程變得更加直觀:

async def encryptFileAndUpload(path):

try:

data = await readFile(path)

ciphertext = await encrypt(data)

await upload(ciphertext)

except:

# 處理錯誤encryptFileAndUpload("/path/to/somefile")

使用await,這些異步的調用又可以寫成一系列按順序完成的代碼,而不失對各步的控制,思路清晰很多。

2. 如何使用Transcrypt?

2.1 安裝和調用

Transcrypt可以通過pip安裝:

$ sudo pip install transcrypt

安裝后,直接在命令行調用就可以了,例如,

$ transcrypt main.py

可以將main.py轉換成js文件。

類似Python 3在執行代碼前會在__pycache__目錄中放置Python字節碼那樣,

transcrypt會將轉換后的文件放到相應的__javascript__目錄。

如果要求轉換的是main.py,則在__javascript__/中,一般會有如下文件:

main.mod.js,這是僅僅包含main.py各行代碼相應js轉譯的文件。

這個文件中會用很多transcrypt的函數“包裝”輸入的Python代碼,但基本上是一對一的對照,

因此可供用戶檢查代碼是否有問題等。

main.js,這是將main.py轉譯為js,并嵌入transcrypt本身需要的js代碼,打包而成的文件。

這個文件可以獨立嵌入到網頁了。

main.min.js。如果見到這個文件,說明transcrypt還進行了代碼壓縮,這個文件應該也可以單獨運行。

代碼壓縮(minify)需要很多運算,耗費時間,在開發程序時不方便。可以使用-n參數,跳過這一步:

$ transcrypt -n main.py

這樣就可以只生成main.js。

2.2 一些坑

Python和Javascript畢竟是兩種語言,雖然transcrypt可以在很大程度上將前者翻譯為后者,

但有些兩種語言內在的不一致,決定了編程時還需要注意許多坑。

在Transcrypt官網的文檔中,詳細列明了各種坑和其理由。一定要仔細閱讀。

2.2.1 類的繼承,方法的重載

在Python中,定義基類和子類,是很方便的事情,有時候這種編程方式會節約大量時間。

在transcrypt中,可以使用類的繼承,但必須在轉譯時,于命令行使用-e6選項。

這樣生成的代碼為ECMAScript 6代碼,才可以啟用這樣的諸多功能。

重載Python的類,自定義諸如__str__,__getattr__或__setattr__這樣的方法,

可以編寫出非常簡明的程序。例如一個模板程序:

class Template:

def __init__(self):

self.__kv = {}

def __str__(self):

return """Welcome to {sitename}!""".format(self.__kv)

def __setattr__(self, key, value):

self.__kv[key] = value

t = Template()

t.sitename = "NeoAtlantis"

print(str(t)) # 輸出 Welcome to NeoAtlantis!

這個程序定義的Template類,只需要像操作一般的類那樣給它的屬性賦值,

然后用str函數令其生成文本即可。這種用法非常直觀,但也必須在啟用了ECMAScript 6轉譯后才能利用。

2.2.2 特殊的方法名稱

如果要在python中調用一個js模塊(比如jQuery的$.get)的get方法,直接調用會出現錯誤。

根據transcrypt文檔的解釋,這是因為在python中,get本身具有特定的用途,

故須使用py_get與js_get區別調用python內部和原生js的get方法。

同理,對于set方法也有類似的規定。

2.2.3 __pragma__: 很多特性的開關

transcrypt提供了一個__pragma__函數,可以在程序中微調轉譯時的行為。

例如,要在python代碼中調用jQuery,不能直接使用$變量,因為$并不是一個規范的Python變量名。

這時,就要用__pragma__為$定義一個別名:

__pragma__("alias", "S", "$")

之后,就可以在程序中用S代替$來調用jQuery了。

__pragma__能進行的調節有許多。

很多情況下,Python本身允許的特性,transcrypt出于效率考慮默認不支持,便需要通過這一函數啟用。請讀者務必參考文檔。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/260610.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/260610.shtml
英文地址,請注明出處:http://en.pswp.cn/news/260610.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

第5章 Python 數字圖像處理(DIP) - 圖像復原與重建8 - 估計噪聲參數

標題估計噪聲參數估計噪聲參數 周期噪聲的參數通常是通過檢測圖像的傅里葉譜來估計的。 只能使用由傳感器生成的圖像時,可由一小片恒定的背景灰度來估計PDF的參數。 來自圖像條帶的數據的最簡單用途是,計算灰度級的均值和方差。考慮由SSS表示的一個條…

python 隨機獲取數組元素_Python創建二維數組的正確姿勢

List (列表)是 Python 中最基本的數據結構。在用法上,它有點類似數組,因為每個列表都有一個下標,下標從 0 開始。因此,我們可以使用 list[1] 來獲取下標對應的值。如果我們深入下列表的底層原理&#xff0c…

Qt學習筆記1

1.Qt引用API時,QString到LPCWSTR的轉換: ::GetPrivateProfileIntW(QString(tr("相關設置")).utf16(),QString(tr("時間間隔")).utf16(),5,filePath.utf16())); 2.引用LPRECT時: RECTappRect; ::GetWindowRect(AppWnd,(LP…

在ubunut下使用pycharm和eclipse進行python遠程調試

我比較喜歡Pycharm,因為這個是JetBrains公司出的python IDE工具,該公司下的java IDE工具——IDEA,無論從界面還是操作上都甩eclipse幾條街,但項目組里有些人使用eclipse比較久了,一時讓他們轉pycharm比較困難&#xff…

CSS:頁腳緊貼底部

2019獨角獸企業重金招聘Python工程師標準>>> 我的練習來源于《CSS揭秘》這本書第7章-41緊貼底部的頁腳這部分內容以及書中提到的鏈接。 方案一 描述:以下方案簡單、干凈、現代并且沒有hack,適用于IE8, Chrome, Firefox, Opera等瀏覽器&#x…

第5章 Python 數字圖像處理(DIP) - 圖像復原與重建9 - 空間濾波 - 均值濾波器 - 算術平均、幾何平均、諧波平均、反諧波平均濾波器

標題只存在噪聲的復原 - 空間濾波均值濾波器算術平均濾波器幾何均值濾波器諧波平均濾波器反(逆)諧波平均濾波器只存在噪聲的復原 - 空間濾波 僅被加性噪聲退化 g(x,y)f(x,y)η(x,y)(5.21)g(x, y) f(x, y) \eta(x, y) \tag{5.21}g(x,y)f(x,y)η(x,y)(5…

librosa能量_librosa與python_speech_features

在語音識別領域,比較常用的兩個模塊就是librosa和python_speech_features了。最近也是在做音樂方向的項目,借此做一下筆記,并記錄一些兩者的差別。下面是兩模塊的官方文檔LibROSA - librosa 0.6.3 documentation?librosa.github.ioWelcome t…

java Unicode轉碼

1 //中文轉UNICODE2 public static String chinaToUnicode(String str) {3 String result "";4 for (int i 0; i < str.length(); i) {5 int chr1 (char) str.charAt(i);6 if (chr1 > 19968 && ch…

oracle-備份工具exp-imp

雖然是按照用戶的方式導出的&#xff0c;但導入之前&#xff0c;還是必須要有相同的用戶存在&#xff0c;刪除用戶以后&#xff0c;是無法進行導入的 --重新創建回zlm用戶 SQL> create user zlm identified by zlm; 盡管zlm用戶的默認表空間是USERS&#xff0c;但是用imp導入…

繼承String?

不能繼承&#xff0c;因為 public final class String extends Objectimplements Serializable, Comparable<String>, CharSequence final修飾的類是不能被繼承的轉載于:https://www.cnblogs.com/crane-practice/p/3666006.html

python中字典數據的特點_Python數據類型(字典)

Python 字典(Dictionary) 字典是另一種可變容器模型&#xff0c;且可存儲任意類型對象。 字典的每個鍵值(key>value)對用冒號(:)分割&#xff0c;每個對之間用逗號(,)分割&#xff0c;整個字典包括在花括號({})中 ,格式如下所示&#xff1a; d {key1: value1, key2: value2}…

第5章 Python 數字圖像處理(DIP) - 圖像復原與重建10 - 空間濾波 - 統計排序濾波器 - 中值、最大值、最小值、中點、修正阿爾法均值濾波器

標題統計排序濾波器中值、最大值、最小值、中點 濾波器修正阿爾法均值濾波器統計排序濾波器 中值、最大值、最小值、中點 濾波器 f^(x,y)median{g(r,c)}(5.27)\hat{f}(x, y) \text{median} \{g(r,c)\} \tag{5.27}f^?(x,y)median{g(r,c)}(5.27) f^(x,y))max{g(r,c)}(5.28)\ha…

如何設置坐標原點值_氨氣檢測儀電化學原理及報警值如何設置

氨氣體檢測儀檢定規程&#xff1a;一般氨氣體檢測儀檢定規程主要是針對技術參數設定的一些標準&#xff0c;具體包含有規程的名稱和范圍、儀器示值誤差、充分性標準差、響應時間、穩定性、報警功能、流量控制器、檢定項目表、檢定操作有數值誤差、重復性、響應時間、穩定性等。…

統計信息及相關說明

統計信息&#xff1a;0 recursive calls20434 db block gets 317970511 consistent gets 0 physical reads 3759764 redo size 382 bytes sent via SQL*Net to client 1061 bytes received via SQL*Net from client 3 SQL*Ne…

Android橫豎屏切換的生命周期

關于Android手機橫豎屏切換時Activity的生命周期問題&#xff0c;網上有很多相似的文章&#xff0c;大多數都是說明在豎屏切換橫屏時Activity會重啟一次&#xff0c;而在橫屏切換豎屏時Activity會重啟兩次。 我本身不太理解這樣設計的意義&#xff0c;并且覺得新版本會解決這個…

python 隨機字符串_python生成隨機數、隨機字符串

python生成隨機數、隨機字符串 import random import string # 隨機整數&#xff1a; print random.randint(1,50) # 隨機選取0到100間的偶數&#xff1a; print random.randrange(0, 101, 2) # 隨機浮點數&#xff1a; print random.random() print random.uniform(1, 10) # 隨…

ACM 會場安排問題

會場安排問題 時間限制&#xff1a;3000 ms | 內存限制&#xff1a;65535 KB難度&#xff1a;4描述學校的小禮堂每天都會有許多活動&#xff0c;有時間這些活動的計劃時間會發生沖突&#xff0c;需要選擇出一些活動進行舉辦。小劉的工作就是安排學校小禮堂的活動&#xff0c;…

第5章 Python 數字圖像處理(DIP) - 圖像復原與重建11 - 空間濾波 - 自適應濾波器 - 自適應局部降噪、自適應中值濾波器

標題自適應濾波器自適應局部降噪濾波器自適應中值濾波器自適應濾波器 自適應局部降噪濾波器 均值是計算平均值的區域上的平均灰度&#xff0c;方差是該區域上的圖像對比度 g(x,y)g(x, y)g(x,y)噪聲圖像在(x,y)(x, y)(x,y)處的值 ση2\sigma_{\eta}^2ση2? 為噪聲的方差&am…

關閉防火墻_從零開始學Linux運維|09.關閉防火墻和SElinux

firewalld是centos7默認的防火墻安全增強型 Linux(Security-Enhanced Linux)簡稱 SELinux初學者建議先關閉,等熟悉了之后再來使用前期聯系中的好多錯誤都有可能是由于沒有關閉或者正確配置上面兩項造成的1.臨時關閉centos7下的防火墻firewalld一行命令就能夠關閉firewalld--&qu…

Discuz!NT - 在線顯示列表 游客 bug 修復

引發bug的條件&#xff1a;當你修改了系統組里面的[游客]組 的名字后&#xff01;&#xff01; 你會發現首頁上底部的在線顯示列表里始終都是顯示"游客"字樣而非你改過得字樣&#xff01;如圖 至此你需要運行一個t-sql腳本去修復這個bug&#xff01;&#xff08;但是…