📜 [專欄新文章] 類 Python 的合約語言 Vyper 開發入門:與 Solidity 差異、用 Truffle 部署、ERC20 賣幣合約實做
✍️ 田少谷 Shao
📥 歡迎投稿: https://medium.com/taipei-ethereum-meetup #徵技術分享文 #使用心得 #教學文 #medium
有鑒於個人近期關注的 Uniswap 及 Curve 皆用 Vyper 實作,索性瀏覽了官方文件並嘗試一些開發工具,希望此文能減少一些讀者初嘗 Vyper 會遇到的麻煩!
Vyper and Solidity
Outline
一. Vyper 極簡介二. 與 Solidity 語法差異三. 開發、開發環境設置 1. 語法高亮 2. 本地 Vyper compiler 安裝 3. 使用 Truffle 操作 ERC20 - 安裝 Truffle - 發幣 - 寫個簡易賣幣合約四. 已知 Remix 問題 五. 結語
一. Vyper 極簡介
Vyper 是除 Solidity 外,以太坊上的另一智能合約 (Smart contract) 語言。其語法和 Python 相近,但畢竟也是寫合約的語言,邏輯差異不大,所以若熟悉 Solidity 應該不難理解用 Vyper 寫出的合約!
Vyper 主要被設計和 Solidity 的區別是安全性及可讀性,這部分會在下一段落及後方的實作中舉例說明。
二. 與 Solidity 語法差異
Vyper 與 Solidity 的差異有許多,在本段只就個人認為感受較深的三點進行說明,其他差異只進行翻譯,有興趣的讀者可以到官方文件詳細了解:https://vyper.readthedocs.io/en/latest/index.html
1. 沒有 modifier
Solidity 常見的 onlyOwner() modifier; 由於 gist 沒有 Solidity 的語法高亮,故截圖
在 Vyper 中單純用 assert 及 assert_modifiable 來進行條件檢查,兩者差別為若要檢查函數執行後的返還值,要用後者,如下圖:
Vyper 寫法
2. 沒有 Class inheritance 繼承
繼承是物件導向程式設計 (OOP) 的核心概念,但各種繼承關係有時候確實很複雜。Vyper 沒有繼承,這無疑大幅地增加了程式可讀性及安全性,以及降低審計程式碼的難度。在此提供一個例子供不熟悉 OOP 複雜之處的讀者有個概念:
source: https://consensys.github.io/smart-contract-best-practices/recommendations/#multiple-inheritance-caution
在上例中,contract A 的 fee 值 (因繼承自 contract B 和 C,故有 fee 一值) 是 5、a 值也是 5 (因繼承自 contract Final,故有 a 一值)。原因是 A 先繼承 B 再繼承 C,因此 contract A 中的 setFee() 是使用了 contract C 的 setFee(),而 a 值是由於 C(5),這代表 contract C 的 constructor (舊版本中即 function C(),函式名稱同 contract 名稱) 被傳入的值為 5。
稍微延伸一下以上概念,將 contract A 改成:contract A is C, B。如此一來,a 值還有 fee 值都會是 3,因為這次 A 先繼承 C 再繼承 B,因此最終吃到的值是 contract B 的。
以上就是 OOP 繼承的複雜之處的簡單範例說明,應該能稍微感受到爲什麼除去繼承後會大幅提高可讀性及安全性,畢竟即使是熟悉 OOP 的人有時頭腦一混亂也會開始懷疑自己寫的程式碼繼承結構是否正確 …
3. 沒有 dynamic array 動態陣列
這應該是目前 Vyper 設計中爭議最大的部分。沒有動態陣列代表在宣告陣列時需要宣告其長度,也就是說 Solidity 中的寫法 uint[], bool[] 等等,這些是不會出現在 Vyper 的。在 Vyper 中只能出現諸如:
# Vyper 的變數宣告方式為 變數名稱: 存取範圍(變數型態(若為陣列給長度))
values: uint256[10]participants: public(address[20])
可以看到上方的 uint256 及 address 兩陣列皆需要宣告長度,不能不宣告而使其動態地配置空間。
沒有動態陣列固然可以確保執行運算的範圍、次數,但一來動態陣列真的很方便、二來在 Solidity 有此功能而 Vyper 卻沒有的情況下可能會造成麻煩,詳見此一討論串:點我。
4. 沒有 inline assembly,程式碼中不會有組合語言
5. 沒有 function overloading,函式不會因傳入的參數數目不同而結果不同
6. 沒有 operator overloading,運算符號不會有不同於預設的自定義功能
7. 沒有無限迴圈,可免於 gas limit attack
8. 十進位定點數 decimal fixed point 而非二進位 (binary) 定點數,詳見:點我
三. 開發、開發環境設置
結論先講
開發 Vyper 的最佳姿勢目前個人認為是在本地裝上 Vyper compiler、用 Truffle 部署,並在撰寫時將檔名後加上 .py 就能有 Python 的語法高亮👌
1. 語法高亮 (syntax highlighting)
有語法高亮絕對是舒服地寫程式的第一步。
Remix 有 Vyper 的語法高亮,但一來個人目前不推薦使用 Remix 來撰寫 Vyper,原因詳見下方 4. 已知 Remix 問題;二來 Remix 的語法高亮其實也沒有很清楚,因此個人推薦:在本地開發,將檔名後加上 .py 就會有 Python 的語法高亮。
2. 本地 Vyper compiler 安裝
照官方說明使用 Python 的虛擬環境 virtualenv:
source: https://vyper.readthedocs.io/en/latest/installing-vyper.html#installing-vyper
簡單兩點提醒:
如果中間那行報錯但確實已經有 Python,則可能是版本問題。依照自己電腦上的版本改成相應的即可,ex: python3.6 改成 python3
進入虛擬環境後(檔案路徑前方應有 vyper-venv 的提示),使用此指令: vyper {檔案名稱}.vy,即可編譯 .vy 檔;使用完畢後輸入 deactivate 即可退出
3. 使用 Truffle 操作 ERC20
安裝 Truffle
Truffle 雖有冗餘的 migration 但也別無他法,畢竟 Remix 目前仍不完善 :(
下載流程可以照官方文件,使用 vyper-example:
source: https://github.com/truffle-box/vyper-example-box
由於我們會接上測試網 Ropsten,因此還要下載 truffle-hdwallet-provider:
source: https://github.com/trufflesuite/truffle-hdwallet-provider
接者就可以開始使用 Vyper 寫合約了!
發幣
由於 Vyper 的官方文件中已經有許多優質範例,因此本文希望來點不一樣但大家卻又很熟悉的…以 ERC20 為例(這千篇一律的主題xD):
用 Curve 的 ERC20 程式碼為範本,發一個幣(又要發…)
寫一個簡易賣幣合約
選擇這個主題一方面畢竟 ERC20 是以太坊的最大宗應用之一,二來有興趣的讀者可以透過讀 ERC20 的程式碼來熟悉 Vyper,並在看過本文的流程後對於用 Vyper+Truffle 來操作 ERC20 有完整的概念!
好的,首先複製一份 Curve 的 ERC20 程式碼(看到就順手拿來用),並複製到 Truffle 所在路徑的 contracts 資料夾中:https://github.com/curvefi/curve-contract/blob/pool_compound/vyper/ERC20.vy
由於第一點希望著重在跑一次流程,因此不改動合約的程式碼。
將 ERC20.vy 複製到 contracts 資料夾中後,到 migrations 資料夾開啟 2_deploy_contracts.js,首先將 require() 中的參數改為 ERC20.vy 的檔名 ERC20,再來依照自己喜好決定幣的名稱、代號、小數點位數及發行總量,輸入於 deployer.deploy() 中。
接著,為了和測試網 Ropsten 互動,需要將以下程式碼寫入 truffle-config.js。
第二行的 privateKeys 是帳號的私鑰。以下實作需要兩個帳號來操作,因此請從錢包匯入兩組私鑰(並非助憶詞)。
在第 13 行中 HDWalletProvider 此函式的第三個參數代表要用第幾個帳號最為預設帳號(部署合約等),第四個函數代表總共匯入幾組帳號。而第二個參數則是需要至 Infura 申請一個 project 來得到串接 Ropsten 的連結。這兩步驟並非本文重點,因此不詳細解說步驟,Google 搜尋關鍵字應該就會找到方法!
接著,就可以輸入以下指令來將代幣發佈到 Ropsten:
truffle deploy --network ropsten
有進入虛擬環境才可以編譯 .vy 檔,若忘記就會收到如下的錯誤訊息:
記得打開虛擬環境才能編譯 .vy 檔
成功後就可以在 contract address 中看到代幣發佈的位置,加入到 Metamask 中就可以看到。本文的例子是維尼代幣 Winnie the Coin, WTC ;)
contract address 便是 ERC20 的所在
Winnie the Coin, WTC
好了,到此測試網上又多了一個測試用的垃圾廢幣。
寫個簡易賣幣合約
賣幣合約中我想要簡單有兩個功能就好:付錢買幣 、結束銷售,以下就是程式碼。買幣的部分就不寫太詳細,固定價格為 0.01 Ether 可以買 500 代幣。
簡單說明幾點:
Solidity 的 constructor() 在 Vyper 中為 Python 風的 __init__():
函式的屬性(public, private, payable 等等)放在函式上方,與 Python 的修飾器位置相同
總之寫法跟 Python 很像,次方也一樣是用兩次乘法代表:**
變數前加上 self 代表是當前合約的變數/全域變數,因此非常容易與函式中的變數/區域變數做區隔
由於已經在第一行匯入了 ERC20 那份合約,因此透過將地址傳入合約當參數,就可以呼叫在該地址的合約:ERC20(self.tokenAddress) 。並且,可以將部署的合約存成一個變數 erc20 較方便
寫完合約後一樣要更改 migrations 資料夾中的 2_deploy_contracts.js 如下,將代幣所在的地址作為參數輸入。
由於先前已經部署過一次了,因此要重置才能再部署第二次,輸入以下指令:
truffle deploy --reset --network ropsten
部署成功之後就要來試著買幣啦!輸入以下來進入 console:
truffle console --network ropsten
成功進入後應該會看到 truffle(ropsten)> 的字樣。接著,首先取得部署的兩合約,並查看是否有返回合約資訊:
# ERC20 及 SellToken 是先前在 2_deploy_contracts.js 中的變數名稱,代表被部署的合約
let instance1 = await ERC20.deployed()instance1 # 印出 instance1 的資訊
let instance2 = await SellToken.deployed()instance2 # 印出 instance2 的資訊
再來,為了讓 SellToken 可以賣幣,要先用 ERC20 的合約匯幣到 SellToken 的合約。因此,輸入以下指令:
instance1.transfer(instance2.address, 10000)
# 這裡數字只要設為 > 500 就可以
接著,我們要利用第二個帳號去買幣(第一個帳號為預設帳號,因此就是代幣擁有者)。將帳號的資訊存入變數 accounts 中,再指定送出交易的帳號是第二個帳號。由於我個人匯入私鑰的順序是將第一個帳號存在 truffle-config.js 的 privateKeys[0]、第二個帳號存在 privateKeys[1],因此第二個帳號的地址就會在 accounts[1] 的位置:
let accounts = await web3.eth.getAccounts()
instance2.buyToken({from: accounts[1], value: 10000000000000000})
# value 為 10^16 是因為在 SellToken 的 buyToken 函式中買一次要 0.01 Ether, 即為 10^16 wei
然後應該就會在自己的第二個帳號中看到匯入的幣了~
最後,由於合約中結束銷售就是一個自殺 selfdestruct 函式,因此可以呼叫看看,第一個帳戶錢包中的錢應該會增加,因為第二個帳戶有付款買幣;並且,可以到 Ropsten 上瀏覽,應該能看到相關提示:
中間 contract 的右上角有 Self Destruct 的樣式
四. 已知 Remix 問題
Remix 目前有兩個版本,只有新版有 Vyper 的編譯器。在此整理目前遇到的問題,如果有人也遇到可以對照一下本處,可以省去很多自我懷疑xD
不會報錯
Remix 的編譯結果有時會是錯的、和本地端編譯出來的結果不同
舉上方的 SellToken 合約為例,將其複製到 Remix 中使用左邊的 Remote Compiler 有錯,但又不報錯 q_q (ERC20 的合約有在同檔案目錄)
左方有紅色三角形,代表編譯失敗,但沒有報錯訊息可以看…
getter function 竟然要花錢
用 Solidity 寫的合約,查詢 public 變數的值應該是不用消耗 gas 的,但不知何故查詢 Vyper 寫的合約的 public 變數卻要消耗 gas,如下圖…
可以看到中下方有 22026 gas 的消耗
Local compiler 無法使用
圖中的 Local Compiler 此選項,個人雖照官方文件執行 vyper-serve 但卻失敗,因此若有讀者成功希望能留個言不吝分享!
五. 結語
Vyper 作為一個比 Solidity 更新的合約語言,在寫程式碼的方面沒什麼問題,但相關的開發工具、學習資源等都遠不及 Solidity。
Vyper 主打的兩個特色:可讀性的部分相信看完上面的讀者應該已經有些感覺;安全性…小白如作者我倒是沒有感受到顯著的不同。況且 Solidity 已經發展許久,很多錯誤的寫法、知名的安全漏洞大家應該也很熟悉了,還有 Openzeppelin 提供安全合約寫法的範本,因此有待以後高人解說安全性是否真的是 Vyper 較好。
有興趣者可以查看 Vyper 的安全報告:點我,大意是目前 Vyper 的編譯器仍有許多問題待改進! (感謝 Chih-Cheng Liang 的提供)
本文對 Vyper 的介紹及其與 Solidity 的差異只講了個大概,欲知更詳細的介紹還是要麻煩讀者前往官方文件了:https://vyper.readthedocs.io/en/latest/index.html
最後,如果本文有任何錯誤,請不吝提出,我會盡快做修正;而如果我的文章有幫助到你,可以看看我的其他文章,歡迎一起交流 :)
田少谷 Shao - Medium
類 Python 的合約語言 Vyper 開發入門:與 Solidity 差異、用 Truffle 部署、ERC20 賣幣合約實做 was originally published in Taipei Ethereum Meetup on Medium, where people are continuing the conversation by highlighting and responding to this story.
👏 歡迎轉載分享鼓掌
「c compiler推薦」的推薦目錄:
- 關於c compiler推薦 在 Taipei Ethereum Meetup Facebook 的精選貼文
- 關於c compiler推薦 在 紀老師程式教學網 Facebook 的精選貼文
- 關於c compiler推薦 在 iThome Facebook 的最佳貼文
- 關於c compiler推薦 在 [問題] C++自學- 看板C_and_CPP - 批踢踢實業坊 的評價
- 關於c compiler推薦 在 [問題] C++ 的編譯器有哪些呢? - c_and_cpp | PTT數位生活 的評價
- 關於c compiler推薦 在 資工系C的編譯器要用哪個 - 中山大學板 | Dcard 的評價
- 關於c compiler推薦 在 [問卦] 哪一個IDE比較好用 | c ide推薦ptt - 旅遊日本住宿評價 的評價
- 關於c compiler推薦 在 初學C語言 | 想推薦你一個Online Compiler | 三米 的評價
c compiler推薦 在 紀老師程式教學網 Facebook 的精選貼文
[好站分享] GitHub 上的瘋狂 C++ 相關資源清單:Awesome-C++
逛國外網站這麼久,很少碰到有資源齊全到讓我倒抽一口涼氣的...這個作者對 C++ 很有愛啊~~
Awesome-C++,是掛在 GitHub 上的一個 C++ 資源清單。收集了 C++ 相關的函式庫、軟體、書籍、文章...還推薦作者覺得也不錯的其它清單。連結如下:
https://github.com/fffaraz/awesome-cpp
一旦點進去,你會被裡面滿滿的超鏈結,把你的腎上腺素濃度打到最高... XD。如果您平常工作與 C++ 相關,您絕對不能錯過這份清單。我簡單列出一下這份清單有什麼:
(以下文長,是寫給英文苦手的讀者看的。英文沒啥問題的朋友,建議直接看原文即可)
一、函式庫與框架
* 標準函式庫(Standard Libraries):
C++ 原生函式庫、POSIX、ISO、GNU 各家出品的標準函式庫都有。
* 程式框架(Frameworks)
「框架」比「函式庫」規格大一點。一般來說,「函式庫」幫你把常用的程式寫好,你只要叫用就好了,是一種幫助你加速完工、但並沒帶來任何新功能的一堆程式碼。「框架」則是替原始 C++ 帶來一些令人驚艷的新功能。不過這種分法,並非絕對的。
* 人工智慧(Artificial Intelligence, AI)相關框架與函式庫
想要催得動這一坨東西,得有點 AI 背景。否則你可能不知道函式庫提供給你「深先搜尋(Depth-first Search)」與「廣先搜尋(Width-first Search)」這些函數怎麼讓那堆冷冰冰的硬體多一點智慧。
* 非同步呼叫所使用的事件佇列(Asynchronous Event Loop)
一般來說,一個程式呼叫另一個程式,「叫人的」得等「被叫的」把事情做完,才能繼續進行下一步。就像一個經理眼睛盯著新手做事、沒辦法回到辦公桌做自己的事一樣,這種模式叫「同步呼叫(Synchronous Call)」。比較好的作法,是你交代完新手該做什麼,就離開回去做自己的事,等新手做完了,再來報告說「我做完了」,這種模式叫「非同步呼叫(Asynchronous Call)」。不過要能做到「非同步」,「叫人者」與「被叫者」之間,得有「事件(Event)」這個機制,讓兩者互相溝通該做的事,以及是否完工。此處提供的,都是讓 C++ 能達成「非同步」機制的函式庫或框架。
* 音效(Audio)相關框架或函式庫
這裡放的,都是讓你的 C++ 能做到讀取音效檔(如:mp3),並用程式碼對該檔進行剪輯、混音...等動作的函式庫或框架。
* 生物(Biology)相關框架或函式庫
這邊的函式庫,可以讓您用 C++ 比對兩條 DNA 序列相似度有多高,或者從一大堆不同樣本的 DNA 中,找出哪條 DNA 與哪條可能有親緣關係...等。
* 命令列(Command Line Interface, CLI)相關框架或函式庫
用這邊的函式庫,可以讓您在命令列跑出一些令人驚艷的效果。如 NCurses 就是一套能在命令列之下,用文字盡量模擬出下拉式選單、按鈕...圖形界面的感覺。
* 壓縮(Compression)相關函式庫
讓您不必瞭解檔案壓縮原理,會叫用相關函數就能做到檔案壓縮。
* 平行處理(Concurrency)相關函式庫
讓 C++ 也能輕易做到同時處理多件事情的函式庫。
* 資料結構相關函式庫(Containers)
提供資料結構內的 B-Tree 與 Hashmaps 等架構,讓 C++ 輕鬆取用。
* 加密(Cryptography)相關函式庫
提供加密解密相關函數。
* 資料庫(Database)相關函式庫
讓 C++ 可以用幾道命令,輕鬆接取 MySQL、MongoDB...等知名資料庫內的資料。
* 除錯、測試、效能(Debug)相關函式庫
雖然原文只用了「Debug」這樣的簡單字眼,但這一區的函式庫包含「單元測試(Unit Test)」、「效能測試(Benchmark)」、「記憶體用量追蹤(Memory Tracking)」等功能的函數。讓您的程式在還沒跑之前,就接受嚴格檢驗,降低發生錯誤的機會。
* 遊戲引擎(Game Engine)
提供一些函數,讓您輕鬆讀入 3D 建模軟體(如:Maya, 3D Studio...)做出來的模型與動畫。並在程式內特定事件(如:碰撞)發生時播放。也提供打光(Shading)、物理函數(如:彈跳、碰撞)...等方便的程式供您取用。這些東西讓您在寫遊戲時,能以更快的效率產出結果。
* 圖形界面(Graphical User Interface, GUI)
讓您用 C++ 建立漂亮的視窗、對話框、核取框、下拉式功能表...等圖形界面。
* 圖形(Graphics)相關函式庫
這部分多與遊戲引擎搭配,提供 2D 圖形處理或 3D 光跡追蹤(Rendering)等「外觀美化」的函數。讓您的遊戲角色或場景,看起來更栩栩如生。
* 影像處理(Image Processing)相關函式庫
包含讀入/繪出各式圖檔(PNG、JPG、GIF...)、光學字元辨識、電腦視覺、讀入/播放各式影片(MP4...)等函數。
* 國際化(Internationalization)相關函式庫
讓您用 C++ 寫出來的程式,可以輕易支援各國語言(當然,各國語言要事先請翻譯社先翻好,這邊只是提供語系切換的機制)。
* 行程間通訊(Inter-Process Communication, IPC)相關函式庫
兩個跑起來的獨立程式(如:兩個執行檔)想在執行過程中交換資料,稱為「行程間通訊」,簡稱 IPC。IPC 雖然不至於難如登天,不過要做到,手續還是很瑣碎的。這邊的函式庫提供好用函數,讓兩個行程交換資料時,變得比較容易。
* JSON 支援相關函式庫
JSON 原文是 JavaScript Object Notation。是一種用「純文字」來表示「資料」的方法。如一筆「李大華、35 歲、手機 0937555666」的資料,用 JSON 表示是這樣的:
[
Name: "李大華",
Age: 35,
Mobile: "0937555666"
]
之後可以讓這樣的資料,流通於瀏覽器與伺服器之間。而 JSON 函式庫,可以快速幫您分析 JSON 表示的資料,將它還原成您要的格式。
* 日誌(Logging)支援函式庫
日誌在「系統稽核」中,是很重要的功能。系統得把「什麼人、等級多高、做了什麼事、何時做的、對哪部分做的、從哪個 IP 過來...」忠實記錄下來。萬一系統出事了,我們就能追查可能是誰搞的。類似「監視器」的功能。這部分的函式庫,可以讓 C++ 輕易做到「日誌」功能,您不用傷腦筋日誌功能該怎麼寫,它已經幫您寫好了。您只要會用就行。
* 機器學習(Machine Learning)相關函式庫
提供如「類神經網路」、「電腦視覺」等進階函式庫,讓您的 C++ 程式有少量人類視覺與思考能力(真的很少量,請不用有太高期待)。
* 數學(Math)相關函式庫
一些線性代數、矩陣運算...等相關數學函數。
* 多媒體(Multimedia)相關函式庫
如:影音串流...等相關函數。
* 網路(Networking)相關函數
提供各種低階網路協定相關函數。如:TCP/IP、HTTP、點對點傳輸、非同步通訊、以及一些與 Facebook 橋接的相關函數。
* 物理模擬(Physics)相關函數
這部分也可以大量用於遊戲程式設計。主要提供一些函數,用來模擬自然界各種物理現象。如水流、風吹、碰撞、彈跳...等。
* 機器人控制(Robotics)相關函數
一堆方便你控制或模擬機器人行為的函數。
* 科學運算(Scientific Computing)
一些在科學上比較用得著的數學運算。如工程數學、傅立葉分析...等。
* 腳本語言控制(Scripting)
包含一些能讓 C++ 與各種腳本語言(JavaScript、PHP、Perl...)橋接的函數。
* 序列化控制(Serialization)
首先解釋一下何謂序列化。序列化可以把程式執行到一半的樣子,如數保存於硬碟中,甚至於可以關機。之後可以把序列化的資料「反序列化」,將它「解凍」還原至記憶體繼續跑,就像當初跑到一半被「冷凍」當下再往下執行一樣。這邊提供許多 C++ 序列化的函式庫。
* 影片處理(Video)
可以讀入/播放各種影片檔的函式庫。
* 虛擬機(Virtual Machines)
這邊提供一些用 C++ 寫出來的「輕量級」虛擬機。所謂虛擬機,是用軟體模擬出硬碟、處理器、記憶體、螢幕,工程師可以在虛擬機內安裝另一個作業系統,就好像安裝作業系統至真實機器一樣。
* 網頁應用軟體框架(Web Application Framework)
集合了一些用 C++ 寫出來的 WWW 伺服器、或開發網頁時用得上的函式庫等。
* XML
如果你希望教會你的 C++ 程式「讀懂」一個 XML 檔在講什麼,這邊提供了一堆 XML 解析器(XML Parser),方便您分析從遠方伺服器傳來的 XML 檔到底想表達什麼樣的資料。
* 其它(Miscellaneous)
一些無法分類的東西,通通塞在這裡。大部分是一些小型的函式庫或 C++ 與其它語言的橋接軟體。
二、C++ 相關軟體
* 編譯器(Compiler)
各類把 C++ 原始碼編成 0 與 1 機械碼的軟體。
* 線上編譯器(Online Compiler)
懶得安裝編譯器的話,現在有一堆線上的編譯器。你上傳原始碼,它會編成機械碼後,丟還個執行檔給你下載。
* 除錯器(Debugger)
一些有名的 C++ 除錯器。當你的程式無法執行時,可以靠它找出到底錯在哪裡。
* 整合式開發環境(Integrated Development Environment, IDE)
IDE 就是把文字編輯器(Editor)、編譯器(Compiler)、除錯器(Debugger)...等軟體整合成一體的軟體。您可以不離開該環境,就能寫碼、編譯、除錯、執行...。
* 軟體建構系統(Build Systems)
簡單說,就是把一些瑣碎動作事先安排好、可以在程式碼修改後,下達一條指令(如:「建構!」),就可全自動一條鞭地從編譯、測試、備份、安裝...一口氣完成的系統。
* 原始碼靜態分析軟體(Static Code Analysis)
丟入原始碼,可以幫你找出哪段程式可能發生錯誤,或者可能造成效能低下。也能找出完全沒被叫用到的原始碼,提醒您刪除。甚至於可以把您的程式碼重排成符合特定格式,統一多人寫碼風格時很有用。
三、其它資源
* API Design 文件
* 有用文章(Articles)
* 推薦書籍(Books)
* 寫碼風格(Coding Style)
* 演講(Talks)
* 影片教學(Videos)
* 有用網站(Web Sites)
* 有用部落格(Weblogs)
* 其它 Awesome C++ 姊妹作(Other Awesome Projects)
四、其它也很棒的清單(Other Awesome Lists)
能看到這行字的,給您拍拍手!辛苦了!希望今天分享的內容您會喜歡!也請您不吝按讚鼓勵,或分享給您 Facebook 的親朋好友!
c compiler推薦 在 iThome Facebook 的最佳貼文
【好文推薦】腦力科技之四:要複雜還是要簡單
成大資工係蘇文鈺教授從台灣企業看輕底層IT(忽略對OS、編譯器等等底層技術的投入)的價值,只顧搶商機的幾個真實小故事,來談臺灣資訊產業的困境和短視。
好文一篇,經蘇老師同意特轉貼!
"許多傳統的技術因為其他領域的技術的高度發展而導致被淘汰,也有許多早被丟棄在一邊多年的技術卻因此而重生。可是因為許多人無法看到幾個世代以來的技術發展過程,也欠缺終身學習的思維,因此常常固執的固守一項當下看來成功的技術與做法,這些人或公司最終都是會招致失敗的後果。
by 成功大學資訊工程學系蘇文鈺教授"
之前的po文,我修了一下文字。若是之前看過的可以跳過。
[腦力科技之四 要複雜還是要簡單]
前面說到的Dave Wilson要價數十萬美元的喇叭WAMM是個大傢伙,整個喇叭是多個分開的模組所構成,非常複雜,所以一般不熟WAMM人要把它調整好是很困難的,難怪要出動Dave Wilson本尊才行。問題是要聽好聲音一定要弄得這麼複雜嗎?
簡單的喇叭,一顆單體裝在一片木板上就可能可以很好聽了。到底要複雜,還是要簡單,其實這問題說是難回答的也不見得,想通後,也可以很簡單。以下是聖嚴師父說過的一個故事:
在我小的時候,有一天傍晚,我父親跟我正好經過一條河邊的小路,有一群鴨子本來在河岸上休息,見到我們父子倆走過,或許是受驚了,也或許是要讓路給我們,總之一群鴨子全部都下了河,從河的這一邊,游到另一邊去。接著又上岸去玩了。
父親看著在河裡游的鴨子,告訴我說:「孩子,你看到了嗎?這群鴨子裡,有大鴨、有小鴨。大鴨游出來的是大的路,小鴨游出來的是小的路。不管是大路還是小路,都是自己游出來的路,而且都到了河的對岸。」
又說:「孩子啊,人要學這些鴨子。你長大之後,不管游出大路或小路都沒有關係。可是不游是不行的,因為不游的話就沒有路可走了。」
也就是說,簡單有簡單的用處,複雜的有複雜的好,做的好,都有活路。
我們這個年紀的人當年用的是Apple II,學程式是從Basic入手,然後是Fortran,接著是Pascal和C,後兩者最大的障礙是要把當時認為抽象的資料結構(data structure)以及資料存放的位址(address)和指標(pointer)的關係搞懂。相對於Basic不知到複雜多少,可是用C能做的事,其實用 Basic也做的到,只不過後者做起來可能會很麻煩而已,程式可讀性與可再被利用性會大幅降低。後來一點我才知道其實所有的高階語言都會透過編譯器(compiler)轉為更低階的assembly(組合語言),所以實際上電腦是依照組合語言一步一步執行的,一個高階語言的指令通常是以多個低階語言來完成。當年在開發工具不足的情況下,我甚至被迫要直接用6502與Z80的機器碼(machine code)來寫程式,因為當時根本沒有如現在這些方便的滑鼠,鍵盤與螢幕可以用。一份工作是要用高階一點的語言來實做,還是用低階的語言來完成,應該依照需求與當下的技術成熟狀況來決定,而不是高階的就一定比較好,低階的就比較一定差,例如多數驅動程式,不用低階語言來做是不行的。反之亦然。
後來我的工作跟使用TI(德州儀器)的C3X與C4X等數位訊號處理器(Digital Signal Processors)有關,一些數位訊號處理的程式我與我的夥伴們都用組合語言來寫,因為編譯器轉出來的程式執行效率實在太差了。可是幾年以後,編譯器越來越強大,所編出來的程式的效能就慢慢提高了,在非關鍵處,我們已經不再堅持用組合語言來寫了。
後來的程式語言越演變越複雜,功能也越來越強大,從簡單的C,到後來的物件導向(Object Oriented),從為數不多的語言,到因為不同的需求而被開發的新語言如Java,LISP,Pearl,Python,Forth等等甚至有為了設計電路的硬體描述語言(HDL) ,慢慢的學校裡對組合語言的要求變少,學生也不願意學,造成許多需要低階語言的工作找不到人來做,不然就只好把人招進了公司後再來訓練。緊接著,為了不同的目的而開發的新的工具軟體變多了,例如為了特殊的資料流(data flow)程式模型而被開發的StreamIt,以至於目前開發iOS App而廣為使用的Object C(我們之後有機會再來談這個語言),為了平行程式所被開發的如OpenMP或MPI(Message Passing Interface),這世界上有關於寫程式這件事所被開發出了來工具多到滿出來,編譯器與中介軟體(middleware)越來越強大,各式各樣的新語言,新應用等等就越多。可是不要忘了,即使是有這麼多五花八門的產物,這世界上有一些角落裡的工作還是需要使用組合語言來做。
有些事需要用複雜的方式來做,有的事卻需要用簡單的方式來做。原本一隻簡單的程式,因為可以平行化,如今我們因為有多核心的機器與可平行的程式模型可以用,所以程式設計師會用更複雜的方式如多執行緒(multithread),資料流(data flow),Map-Reduce(如Hadoop),CUDA與OpenCL等來實做,程式的複雜度看起來提高很多,可是執行所需的時間實際上卻大幅降低。又如,在數位訊號處理裡常用的旋積(Convolution),本來是可以用沒幾行的程式就可以寫出來,但是因為快速富利葉轉換(FFT)的關係,讓我們可以在頻率域(Frequency Domain)裡運算以減少計算時間,但是程式複雜度卻高出許多。可是,因為多核心架構硬體與平行的程式模型的出現,加上時間域(Time Domain)的旋積具備高度可平行化的特性,現在反而是回到時間域來計算要快得多,同時也少了一些在頻率域(Frequency Domain)運算所造成的缺點,過去為了在頻率域運算所開發出來的演算法反而變得沒有多大用處了。
許多傳統的技術因為其他領域的技術的高度發展而導致被淘汰,也有許多早被丟棄在一邊多年的技術卻因此而重生。可是因為許多人無法看到幾個世代以來的技術發展過程,也欠缺終身學習的思維,因此常常固執的固守一項當下看來成功的技術與做法,這些人或公司最終都是會招致失敗的後果。
以上我們說了許多軟體的發展,接著來說硬體,尤其是電腦的核心,CPU(中央處理單元),也就是大家常聽到的Intel Pentium,IBM PowerPC或是ARM Cortex等等。早年的CPU如Apple II用的6502到今日的主流多核心CPU,其複雜度不知道已經高出多少倍,30年前的大型主機(我大學時用的是CDC Cyber,全校共用)的計算能力可能比不上今天的一部桌上型電腦。有一陣子,簡單架構的CPU不容易被聽到(但是實際上他們的用處很廣呢!),一般人知道的CPU都是INTEL出的(因為廣告打得兇),那時的人類似乎除了INTEL X86架構的CPU之外都不需要其他的了。可是曾幾何時,INTEL感受到ARM的架構簡單的省電CPU的強力威脅,所以INTEL也希望把它的CPU變成簡單又省電,但是與此同時,ARM卻在把它的CPU變得功能更強大,但是卻也更耗電。你們說,這兩家公司在爭的商機是甚麼呢?相信只要在這個產業的人都知道他們在玩什麼把戲。大家都知道的東西,在CPU設計落後先進國家的台灣在高階CPU上也就沒什麼好搶的了,那台灣的機會在哪裡呢?(當然,現在的聯發科跟晶心科技這兩家策略與市場都不一樣的公司看來是很有機會佔有一定的市場,有興趣的人可以去研究一下這兩家公司的CPU策略)
有一天,有朋友打電話給我,聊起他現在的公司也在做CPU,而且是八位元,或甚至位元數更低的CPU。我說,這麼低單價的東西有什麼好做的。他說,其實市場的量真正大的是簡單型的CPU,因為太多應用只需要用到簡單的CPU,這時連8051都還嫌太複雜,而且目前設計界常用的Arduino也可以在稍微複雜一點的八位元CPU跑起來。只要做的夠便宜夠省電,利潤還是有的。但是這其中還有一個大問題,那就是即使是這麼簡單的CPU,在今天的情況,工具鍊(toolchain)還是要完整,才會賣得出去。他問我可不可以幫他做編譯器,我說這非我專長,實在是愛莫能助。我不禁想,這年頭連賣一顆幾毛錢的CPU都要開始建完整工具鍊了,這錢還真難賺啊!
又有一次,有間廠商打電話過來問我有沒有興趣做一個建教合作計畫,是關於多核心的系統軟體的。那時候我一聽到多核心,腎上腺素就上來了,也沒多問細節就說可以見面討論。過兩天,我們一起聚在一起開了個會,才知道這個多核心原來是拿8051來當核心。我心想,連8051都拿來做多核心,會不會太奇怪。不過既然廠商堅持有他們的市場與考量,也可以賣得出去,我這商場門外漢就不好說甚麼了。接下來廠商希望我們可以幫忙做兩件事,第一件是為這顆多核心打造一個多核心作業系統,第二件是做一套中介軟體讓不同核心之間可以快速交換資料。當我心裡還在盤算著,且認為這應該可以做得到的時候,接著聽到的話讓我差點從椅子上掉下來。他說,但是這一切希望在16K bytes之內做到,而且在半年內做完,經費是30萬。接著我只能說我願意考慮看看,其實心裡說的是謝謝再連絡並祝福他們會成功,一刻鐘後我堆滿一臉笑容來隱藏底下的鐵青送他們出門。
這些事讓我想起來台灣過去幾年有關IC設計的問題,甚至是更多產業所面對的問題。那就是太重視硬體了,以為只要把硬體做出來,就可以賣出去的時代早就已經過去了,而目前全世界最大的高科技公司其實都是軟體為主的公司,連聯發科的軟體工程師數目早就超過硬體工程師的數目了。假如連一顆八位元的不到的CPU都需要一大堆軟體工具鍊,那麼我實在不清楚很多公司只注重看來是實際出貨用的硬體在想什麼,會逐漸失去商機不奇怪啊!我自己會想,要是早個十年我知道軟體的工具練會這麼重要,那麼我不就賺翻了嗎?可是上面的第二個故事告訴我,在台灣,不被重視的就是不被重視,早做也沒用。很多廠商把技術看得太廉價了,但是這家公司至少還願意出錢,有的台灣公司即使本身很賺錢卻根本就連錢都不出就想獲得技術。
2010之前的好幾年,韓國的政府讓許多家大學(我沒記錯的話是八家,連漢陽與首爾都在其中),參與企業(就是三星啦!)一起trace Android的核心的時候,台灣在做甚麼呢?大喊自由軟體,然後只要寫寫不知道能不能用的Java App就可以有獎金或補助。等到三星智慧型手機崛起,火燒屁股時,才急急忙忙由政府底下的若干研究單位出面協調,同時希望學界也能出面幫忙。
這整件事的荒謬在於,第一,商場如戰場,都火燒屁股,要馬上上戰場去賣的東西讓學界來幫忙怎麼會來得及呢?第二,學生寫的軟體你敢用嗎?一旦有bug不是退貨退到瘋掉?第三,這種核心技術早就該知道要做了,不然派個探子去美國,甚至是韓國轉一圈,也知道人家在做甚麼。然後,既然都火燒屁股又要找學界專家來幫忙,為什麼不乾脆花大錢挖學界懂這東西的一整個團隊進公司體系,還要找官方與半官方的機構出面協調,這不是浪費時間呢?台灣不是最流行超時工作,讓工程師燒肝(燒乾)工作的嗎?高薪一堆人進來,以台灣工程師的素質之高,其實不會沒救的。不過,我看到的情況只能用失望兩個字來形容。
有時人要挖空心思才可以看到商機,有時只要好好照著道理來做就會有商機,賣系統(不管是複雜到手機還是其他簡單的系統應用IC)卻不重視軟體就是沒照著道理來做。目前台灣所製造的電腦產品,只要是要用到稍微大型的軟體系統如Android,或甚至是小到一個小型的RTOS(即時作業系統),有多少是台灣所原創的呢?不能原創的原因很多,公司不重視軟體人才此其一,會教又提供學生實作機會的學校不多(因為做這類苦工無法出High Impact Factor的論文啊!)也是主因,政府科技與教育政策一樣難辭其咎。以編譯器(compiler)這樣傳統的學問來說,不管時代怎麼變,不變的是它對產業總是非常的重要,學校裡有多少人還在做編譯器的研究呢?再來恐怕都要找不到人來教了,因為有多少教授願意做一個傳統又難以發表High Impact Factor論文的研究呢?過幾年,整個硬體產業要是變成硬體慘業,我是一點也不意外。即使沒完蛋,還不是要乖乖每年繳一大堆權利金給外國提供軟體的廠商嗎?
你若是問我,難道台灣真的沒有那種看到軟體工具鍊與大型軟體的機會,堅持信念,終於媳婦熬成婆的團隊嗎?當然有,我也好希望我也是其中之一。可惜我沒有這麼堅強的毅力,要不然也不用在這裡狗吠火車了。
前面說過的話,這裡再重複一遍,但是用意與前面不同,這裡是希望為上面這幾段故事做小結:
許多傳統的技術因為其他領域的技術的高度發展而導致被淘汰,也有許多早被丟棄在一邊多年的技術卻因此而重生。可是因為許多人無法看到幾個世代以來的技術發展過程,也欠缺終身學習的思維,因此常常固執的固守一項當下看來成功的技術與做法,這些人或公司最終都是會招致失敗的後果。
時代在改變,有些事也會跟著變,但是有些事卻也一直不變,變與不變之間,要視實際狀況決定。就跟聖嚴師父說的一樣,大鴨子與小鴨子,只要願意努力前進,都可以游出自己的路。
c compiler推薦 在 [問題] C++ 的編譯器有哪些呢? - c_and_cpp | PTT數位生活 的美食出口停車場
4) Borland C++ Builder (BCB) Borland 公司試圖重新找回C/C++ compiler 市場的大作。 ... 尤其是資料庫)程式的人來說,非常方便;然而,不推薦C/C++ 的初學者使用! ... <看更多>
c compiler推薦 在 資工系C的編譯器要用哪個 - 中山大學板 | Dcard 的美食出口停車場
... 我是今年入學的資工大一菜鳥,想請問學長姐剛開始上課如果是用MAC的都是用哪個編譯器寫程式呢~(C), ... 有推薦非本科系修的python相關課程嗎. ... <看更多>
c compiler推薦 在 [問題] C++自學- 看板C_and_CPP - 批踢踢實業坊 的美食出口停車場
好啦我知道這問題好像問過很多次了@@
小弟我高三生剛考完學測,分數剛好能上台大資工(第一階段應該能過
想說就順手用這個學期學C++
經驗嘛...高中有發一本教科書長這樣https://ppt.cc/bE73
但是礙於自己特殊班的關係,整整三年都沒資訊課
高二上曾自己翻此書來學,大概學到陣列(按此書目錄的話)
接著因為要準備學測就停止了
---以上前言---
總之想趁這段時間學
短期目標的話是應付4.12第二階段的程式設計考試(來不及的話就先準備數學筆試
長期的話就是為未來程設部分打底子
稍微爬文有人說可以先從python等比較簡單的入門
不過我想說不如就繼續學C++,感覺還撐得住
主要問題有幾個:
1.書
我直覺是上面那本不太夠用,想要買本正式點的
當然那本可以的話就是繼續用
爬文有爬到C++ Primer好像不錯?
中譯本跟原文書各有哪些優缺?
或是推薦哪些書?
另外傳說中的白皮書有建議看嗎?雖然是講C語言的
2.編譯器(是這樣說沒錯吧?
一直以來都是用書上附的dev-C++
不過爬文發現dev好像不建議用?
那麼有其他推薦的編譯器嗎?
如果丟google抓不到的話煩請提供入手方法謝謝@@
3.方式
因為還是學生所以平日都是晚上才用的到電腦
白天只有紙筆書有辦法念C++嗎(手寫程式碼之類的雖然不能當下執行感覺很無用@@
不然就是念些別的或跟學校借筆電看看
4.其他
有甚麼其他建議都歡迎提供謝謝XD
--
ps.我知道大家都說C++比較複雜,可是不知為何就想從C++開始XD
當然要是真的效率太差我就先轉而準備數學考試
先保住有大學念XD
之後再學也是可以
--
※ 發信站: 批踢踢實業坊(ptt.cc), 來自: 1.174.204.224
※ 文章網址: https://www.ptt.cc/bbs/C_and_CPP/M.1424873055.A.96B.html
那C跟C++在互相承接上有甚麼差別嗎?
因為學C++比較大部分也是自己想學XD
我大概資訊比較夠了之後下周開始念這樣
※ 編輯: paulpork (1.174.204.224), 02/25/2015 22:15:37
主要是想推薦書籍啦
有書之後其他都好辦
※ 編輯: paulpork (1.174.204.224), 02/25/2015 22:17:19
八卦聽了那麼多婉君
結果真的有一位那麼厲害的婉君阿!
(丟google好像一堆人叫婉君..
我有看過一些考古題,感覺同樣坐好幾個小時
數學要算一二十題,程設卻只有四題(當然兩種科目一題的時間差很多啦XD
感覺考程設會好些吧?
有位版友站內信給我很多建議,還有考古題XD
會先正常念大概剩兩三周時開始解題目,希望來的及啦ww
--
感謝各位版友的意見!
目前會決定先用gcc 然後用劉邦鋒教授的書
不過台大出版那邊這幾天好像沒開@@,大概要下周我哥才會寄回家XD
二階如果過了之後有閒再去碰上面提到的好多書0.0
也熟悉一下VS
希望上大學時是C和C++都會用啦XD
※ 編輯: paulpork (1.174.204.181), 02/28/2015 20:07:48
... <看更多>