Julia 簡介/REPL
julia 程式預設情況下會啟動互動式 REPL,即讀取/評估/列印/迴圈。它允許您輸入 Julia 程式碼表達式並立即看到評估結果列印在螢幕上。它
- Reads 您輸入的內容;
- Evaluates 它;
- Prints 出返回值;然後
- Loops 回來並重復所有操作。
REPL 是開始嘗試學習該語言的好地方。但是,它不是執行任何規模的嚴肅程式設計工作的最佳環境——為此,文字編輯器或互動式筆記本環境(例如 IJulia/Jupyter)是更好的選擇。但使用 REPL 有一些優勢:它很簡單,而且無需任何安裝或配置即可使用。它還內建了一個幫助系統。
您輸入一些 Julia 程式碼,然後按回車/Enter 鍵。Julia 會評估您輸入的內容並返回結果
julia> 42 <Return/Enter> 42 julia>
如果您使用的是 Jupyter(IPython)筆記本,您可能需要按 Control-Enter 或 Shift-Enter。
如果您不想看到打印出的表示式結果,請在表示式末尾使用分號
julia> 42; julia>
此外,如果您想訪問在 REPL 中輸入的最後一個表示式的值,它儲存在變數 ans 中
julia> ans 42
如果您沒有在第一行完成表示式,請繼續輸入直到完成。例如
julia> 2 + <Return/Enter>
現在 Julia 會耐心地等待您完成表示式
2 <Return/Enter>
然後您將看到答案
4 julia>
輸入一個問號 ?
julia> ?
您將立即切換到幫助模式,並且提示符將變為黃色(在終端中)
help?>
現在您可以輸入某件事的名稱(函式名稱應該不帶括號)
help?> exit search: exit atexit textwidth process_exited method_exists indexin nextind IndexLinear TextDisplay istextmime exit(code=0) Stop the program with an exit code. The default exit code is zero, indicating that the program completed successfully. In an interactive session, exit() can be called with the keyboard shortcut ^D. julia>
注意幫助系統嘗試找到所有與您輸入的字母匹配的單詞,並向您顯示它找到的內容。
如果您想搜尋文件,可以使用 apropos 和搜尋字串
julia> apropos("determinant")
LinearAlgebra.det
LinearAlgebra.logabsdet
LinearAlgebra.logdet
您將看到一個列表,其中包含名稱或描述中包含該字串的函式。
julia> apropos("natural log")
Base.log
Base.log1p
help?> log
search: log log2 log1p log10 logging logspace Clong Clonglong Culong Culonglong task_local_storage
log(b,x)
Compute the base b logarithm of x. Throws DomainError for negative Real arguments.
等等。
如果您輸入一個分號
julia> ;
您將立即切換到 shell 模式
shell>
(並且提示符將變為紅色)。此模式下可用的命令是您的系統命令列 shell 使用的命令。在 shell 模式下,您可以輸入任何 shell(即非 Julia)命令並檢視結果
shell> ls file.txt executable.exe directory file2.txt
您如何退出 shell 模式取決於您的 Julia 版本
- 在 Julia 1.6 及更高版本中,shell 模式是“粘性”(永續性)。按 Backspace 作為第一個字元,或 CTRL+C,返回
julia>提示符 - 在早期的 Julia 版本中,提示符會立即切換回
julia>,因此您每次想發出 shell 命令時都必須輸入一個分號。
如果您輸入一個右括號作為第一個字元
julia> ]
您將立即切換到包模式
(v1.1) pkg>
這是您執行包管理任務的地方,例如新增包、測試包等等。
要在空白行上按 Backspace 或 CTRL+C 退出包模式。
以下是 REPL 提示符下可用的其他一些有用的互動式函式和宏
varinfo()– 列印有關模組中匯出的全域性變數的資訊
julia> varinfo() name size summary –––––––––––––––– ––––––––––– ––––––––––– Base Module Core Module InteractiveUtils 222.893 KiB Module Main Module ans 1.285 KiB Markdown.MD
@which– 告訴您將為函式和特定引數呼叫哪個方法
julia> @which sin(3) sin(x::Real) in Base.Math at special/trig.jl:53
versioninfo()– 獲取 Julia 版本和平臺資訊
julia> versioninfo() Julia Version 1.1.0 Commit 80516ca202 (2019-01-21 21:24 UTC) Platform Info: OS: Linux (x86_64-pc-linux-gnu) CPU: Intel(R) Core(TM) i7-3770 CPU @ 3.40GHz WORD_SIZE: 64 LIBM: libopenlibm LLVM: libLLVM-6.0.1 (ORCJIT, ivybridge)
還有一個快速獲取版本的方法
julia> VERSION v"1.1.0"
edit("pathname")– 啟動預設編輯器並開啟檔案pathname以進行編輯
@edit rand()– 啟動預設編輯器並開啟包含內建函式rand()定義的檔案
less("filename-in-current-directory")– 在分頁器中顯示檔案
clipboard("stuff")– 將“東西”複製到系統剪貼簿
clipboard()– 將剪貼簿內容貼上到當前 REPL 行
dump(x)– 在螢幕上顯示有關 Julia 物件x的資訊
names(x)– 獲取模組x匯出的名稱陣列
fieldnames(typeof(x))– 獲取屬於型別x的符號的資料欄位陣列
TAB 鍵通常能夠完成(或建議完成)您開始輸入的名稱。例如,如果我輸入 w 然後按 TAB 鍵(當有多個選項時按兩次),所有以 'w' 開頭的當前可用函式都會列出
julia> w <TAB> wait walkdir which while widemul widen withenv write
這適用於 Julia 實體以及 shell 和包模式。例如,以下是如何從 Julia 內部導航到目錄
shell> cd ~ /Users/me shell> cd Doc <TAB> shell> cd Documents/ shell> ls ...
請記住,您可以使用 ? 和輸入其完整名稱(或使用 TAB 完成)來獲取有關函式的幫助。
TAB 完成也適用於 Unicode 符號:例如,輸入 \alp 並按 TAB 鍵獲取 \alpha,然後再次按 TAB 鍵獲取 α。以及對於 Emoji:例如,輸入 \:fe 並按 TAB 鍵獲取 \:ferris_wheel:,然後再次按 TAB 鍵獲取 🎡。
您可以使用向上和向下箭頭鍵檢視以前命令的記錄(並且您可以退出並重新啟動而不會清除該歷史記錄)。因此,您不必重新輸入一個長的多行表示式,因為您可以從歷史記錄中調出它。如果您輸入了大量的表示式,您可以透過按 Ctrl-R 和 Ctrl-S 在前後搜尋它們。
Julia 的 REPL 支援一些功能,使命令列輸入更有效率,這些功能繫結到特定的按鍵組合。例如,Alt+b 向後一個詞,而 Alt+f 向前一個詞。完整的按鍵繫結列表以及自定義它們的說明可以在 REPL 文件 中找到。請注意,一些編輯器,例如 VS Code,可能會覆蓋某些按鍵組合。
範圍和效能
[edit | edit source]關於 REPL 的一個警告。REPL 在 Julia 的全域性範圍級別執行。通常,在編寫更長的程式碼時,您會將程式碼放在函式內部,並將函式組織成模組和包。當您的程式碼被組織成函式時,Julia 的編譯器會更有效地工作,並且您的程式碼執行速度會更快。在頂層還有一些事情您無法做到,例如為變數的值指定型別。
更改提示並自定義您的 Julia 會話
[edit | edit source]以下 Julia 檔案在每次啟動 Julia 時執行(除非您使用 startup-file=no 選項)。
~/.julia/config/startup.jl
這使您可以載入您知道以後會需要的任何包。例如,如果您想自動自定義您的 REPL 會話,您可以安裝 Julia 包 OhMyREPL.jl (https://github.com/KristofferC/OhMyREPL.jl) ,它允許您自定義 REPL 的外觀和行為,然後,在啟動檔案中
using OhMyREPL
如果您只想在每次啟動 Julia 會話時設定提示,您只需新增以下說明
using REPL
function myrepl(repl)
repl.interface = REPL.setup_interface(repl)
repl.interface.modes[1].prompt = "julia-$(VERSION.major).$(VERSION.minor)> "
return
end
atreplinit(myrepl)
這只是將當前 REPL 提示設定為顯示您的會話正在使用的 Julia 版本號。
Julia 和數學
[edit | edit source]您可以使用 Julia 作為強大的計算器,使用 REPL。這也是一個好習慣。(這是互動式程式語言介紹中的傳統,也是認識語言的好方法。)
julia> 1000000 / 7 142857.14285714287
輸入數字
[edit | edit source]世界上一半的人使用逗號 (,) 將長數字分成三組,另一半使用句點 (.)。(剩下的人使用科學計數法……)在 Julia 中,您可以使用下劃線 (_) 來分隔數字組
julia> 1_000_000 - 2_015 997985
雖然您不會在響應中看到一個。
要使用科學計數法,只需輸入“e”(或“E”)並且不要新增任何空格
julia> planck_length = 1.61619997e-34
要輸入虛數,請使用 im
julia> (1 + 0.5im) * 2 2.0 + 1.0im
運算子作為函式
[edit | edit source]julia> 2 + 2 4 julia> 2 + 3 + 4 9
新增數字的等效形式是
julia> +(2, 2) 4
您通常在值之間使用的運算子是普通的 Julia 函式,並且可以像其他函式一樣使用。同樣
julia> 2 + 3 + 4 9
可以寫成
julia> +(2, 3, 4) 9
和
julia> 2 * 3 * 4 24
可以寫成
julia> *(2,3,4) 24
提供了一些數學常數
julia> pi π = 3.1415926535897...
您可以在 MathConstants 模組中找到其他數學常數
julia> Base.MathConstants.golden φ = 1.6180339887498... julia> Base.MathConstants.e e = 2.7182818284590...
所有常見的運算子都可用
julia> 2 + 3 - 4 * 5 / 6 % 7 1.6666666666666665
請注意運算子的優先順序。在這種情況下,它是
((2 + 3) - ((4 * 5) / 6) % 7)
如果您想檢查運算子的優先順序,請將表示式括在 :( 和 ) 中
julia> :(2 + 3 - 4 * 5 / 6 % 7) :((2 + 3) - ((4 * 5) / 6) % 7)
(有關此內容的更多資訊,請參閱 超程式設計)。
乘法通常寫成 *,但當將變數乘以數字文字時,可以省略。
julia> x = 2 2 julia> 2x + 1 5
julia> 10x + 4x - 3x/2 + 1 26.0
這使得方程更容易編寫。
有時您需要括號來控制求值順序
julia> (1 + sqrt(5)) / 2 1.618033988749895
需要注意的其他一些運算子包括
^冪%餘數
要建立有理數,請使用兩個斜槓 (//)
julia> x = 666//999 2//3
從技術上講,/ 表示“右除”。還有左除“\”。對於數字,x/y = y\x。但是,對於向量和矩陣,x = A\y 解 A*x = y,而 x = y/A 解 x*A = y。
標準算術運算子還有一些特殊的更新版本,您可以使用它們快速更新變數
+=-=*=/=\=%=^=
例如,在定義一個變數 x 後
julia> x = 5 5
您可以為它新增 2
julia> x += 2 7
然後將其乘以 100
julia> x *= 100 700
然後將其簡化為模 11 值
julia> x %= 11 7
有一些按元素運算子可以作用於陣列。這意味著您可以按元素乘以兩個陣列
julia> [2,4] .* [10, 20]
2-element Array{Int64,1}:
20
80
陣列是 Julia 的基礎,因此在本書中擁有自己的章節。
如果您使用 / 除兩個整數,答案始終是浮點數。如果您使用過 Python 版本 2,您會記得 Python 返回一個整數結果。Python (3) 現在返回一個浮點數。
Julia 提供了一個整數除法運算子 ÷(鍵入 \div TAB,或使用函式版本 div()。當您想要整數結果而不是 / 返回的浮點數時,應該使用此運算子。
julia> 3 ÷ 2 1 julia> div(3, 2) 1
請注意,Julia 不會將答案轉換為整數型別,即使結果實際上是一個整數。
julia> div(3, 2.0) 1.0
這是為了避免型別不穩定問題,這會減慢您的程式碼速度。
整數溢位
[edit | edit source]如果您認為您的計算將超出 64 位限制,請透過將 big 函式應用於運算元來選擇大整數,並將它們儲存為大數
julia> 2^64 # oops 0 julia> big(2)^64 # better 18446744073709551616 julia> 2^big(64) # equally better 18446744073709551616
要獲得 Julia 程式的最快執行速度,您應該瞭解如何儲存您的資料和變數,而不會引入“型別不穩定”。
進位制
[edit | edit source]在使用 REPL 作為計算器時,這些方便的實用程式函式可能會有用。
bitstring() 函式顯示數字的文字二進位制表示形式,如儲存的那樣
julia> bitstring(20.0) "0100000000110100000000000000000000000000000000000000000000000000" julia> bitstring(20) "0000000000000000000000000000000000000000000000000000000000010100"
請注意,浮點數“版本”的儲存方式與預期一樣。
要從二進位制字串返回到十進位制,您可以使用 parse(),它接受目標型別和進位制
julia> parse(Int, "0000011", base=2) 3 julia> parse(Int, "DecaffBad", base=16) 59805531053
要以 10 以外的進位制工作,請使用 string 函式將整數轉換為字串
julia> string(65535, base=16) "ffff" julia> string(64, base=8) "100"
而 digits(number, base=b) 返回一個數組,該陣列包含 number 在給定進制中的數字
julia> digits(255, base=16)
2-element Array{Int64,1}:
15
15
變數
[edit | edit source]在此表示式中
julia> x = 3
x 是一個變數,是資料物件的命名儲存位置。在 Julia 中,變數的命名方式幾乎可以隨心所欲,但不要以數字或標點符號開頭變數名。如果需要,您可以使用 Unicode 字元。
要分配值,請使用一個等號。
julia> a = 1 1 julia> b = 2 2 julia> c = 3 3
要測試相等性,您應該使用 == 運算子或 isequal() 函式。
在 Julia 中,您也可以同時分配多個變數
julia> a, b = 5, 3 (5,3)
請注意,此表示式的返回值是一個括號包圍的逗號分隔的元素有序列表:簡稱為元組。
julia> a 5 julia> b 3
數字和變數相乘
[edit | edit source]值得重複的是,您可以用數字開頭變數名來相乘它們,而不必使用星號 (*)。例如
julia> x = 42 42 julia> 2x 84 julia> .5x 21.0 julia> 2pi 6.283185307179586
特殊字元
[edit | edit source]Julia REPL 提供了對特殊字元的輕鬆訪問,例如希臘字母字元、下標和特殊數學符號。如果您鍵入反斜槓,那麼您可以鍵入一個字串(通常是等效的 LATEX 字串)來插入相應的字元。例如,如果您鍵入
julia> \sqrt<TAB>
Julia 用一個平方根符號替換了 \sqrt。
julia> √
其他一些例子
| \pi | π |
| \Gamma | Γ |
| \mercury | ☿ |
| \degree | ° |
| \cdot | ⋅ |
| \in | ∈ |
完整的列表在 Julia 原始碼中。作為一般原則,在 Julia 中,建議您檢視原始碼,因此有一些有用的內建函式可以檢視 Julia 原始檔。例如,在 macOS 上,這些符號儲存在
julia> less("/Applications/Julia-1.0.app/Contents/Resources/julia/share/julia/stdlib/v1.0/REPL/src/latex_symbols.jl")
less 會透過分頁器執行檔案(即 Unix 中的 less 命令)。如果您膽大,可以嘗試使用 edit() 而不是 less()。這將啟動一個編輯器並開啟檔案。
您也可以在 REPL 中使用 Emoji 和其他 Unicode 字元。
對於 emoji,在反斜槓後輸入 Emoji 字元名稱,並在冒號之間,然後按 <TAB>
julia> \:id: <TAB>
這將變為
julia> 🆔
您可以在 https://docs.julialang.org/en/latest/manual/unicode-input/#Unicode-Input-1 中找到列表。
輸入不在此列表中的 Unicode 符號是可能的,但更依賴於作業系統:在 macOS 上,您在鍵入 Unicode 十六進位制數字時“按住”Ctrl/Alt 鍵(在啟用 Unicode 十六進位制輸入鍵盤的情況下);在 Windows 上,它是 Ctrl+Shift+u 後面跟著十六進位制數字。
julia> ✎ = 3 3 julia> ✎ 3
數學函式
[edit | edit source]由於 Julia 特別適合科學和技術計算,因此您可以立即使用許多數學函式,而且您通常不必匯入它們或使用字首——它們已經可用。
三角函式期望以弧度為單位的值
julia> sin(pi / 2) 1.0
但也有基於度的版本:sind(90) 查詢 90 度的正弦。使用 deg2rad() 和 rad2deg() 在度和弧度之間轉換。
還有很多對數函式
julia> log(12) 2.4849066497880004
以及精確的 hypot() 函式
julia> hypot(3, 4) 5.0
norm() 函式(在透過“using LinearAlgebra”載入後)返回向量或矩陣的“p”範數。這是 divrem()
julia> divrem(13, 3) # returns the division and the remainder (4,1)
還有數十種其他函式。
有一個名為 ans 的系統範圍內的變數,它會記住最近的結果,以便您可以在下一個表示式中使用它。
julia> 1 * 2 * 3 * 4 * 5 120 julia> ans/10 12.0
練習
[edit | edit source]猜猜,然後使用幫助系統找出 mod2pi() 和 isapprox() 是做什麼的。
此處描述了與 Julia 一起提供的所有標準函式:[1]
隨機數
[edit | edit source]rand() – 獲取一個介於 0 和 1 之間的隨機 Float64
julia> rand() 0.11258244478647295
rand(2, 2) – 一個維度為 2, 2 的 Float64 陣列
rand(type, 2, 2) – 一個維度為 2, 2 的此型別值的陣列
rand(range, dims) – 在一個範圍內(包括兩個端點)的數字陣列,具有指定的維度
julia> rand(0:10, 6)
6-element Array{Int64,1}:
6
7
9
6
3
10
(有關範圍物件的更多資訊,請參見陣列章節。)
如果告訴它,rand() 函式可以透過傳遞 Bool 關鍵字來生成一個真或假值
julia> rand(Bool) false
或一堆真值和假值
julia> rand(Bool, 20)
20-element Array{Bool,1}:
false
true
false
false
false
true
true
false
false
false
false
false
false
false
true
true
false
true
true
false
分佈中的隨機數
[edit | edit source]randn() 為您提供一個均值為 0,標準差為 1 的正態分佈中的隨機數。randn(n) 為您提供 n 個這樣的數字
julia> randn()
0.8060073309441075
julia> randn(10)
10-element Array{Float64,1}:
1.3261528248041754
1.9203896217047232
-0.17640138484904164
1.0099294365771374
-0.9060606885634369
1.739192165935964
1.375790854463711
-0.6581841725500879
0.11190904953985797
2.798450557786332
如果您已經安裝了 Plots 繪圖包,您可以繪製它
julia> using Plots; gr()
julia> histogram(randn(10000), nbins=100)
播種隨機數生成器
[edit | edit source]Random 包包含更多隨機函式,例如 randperm()、shuffle() 和 seed!。
在使用隨機數之前,您可以使用特定值播種隨機數生成器。這確保了後續的隨機數將遵循相同的序列,如果它們從同一個種子開始。您可以使用 seed!() 或 MersenneTwister() 函式播種生成器。
新增 Random 包後,您可以執行
julia> using Random
julia> Random.seed!(10);
julia> rand(0:10, 6)
6-element Array{Int64,1}:
6
5
9
1
1
0
julia> rand(0:10, 6)
6-element Array{Int64,1}:
10
3
6
8
0
1
重新啟動 Julia 後,相同的種子保證相同的隨機數。
簡單的鍵盤輸入
[edit | edit source]以下是如何編寫和執行從鍵盤讀取輸入的函式的示例
julia> function areaofcircle()
print("What's the radius?")
r = parse(Float64, readline(stdin))
print("a circle with radius $r has an area of:")
println(π * r^2)
end
areaofcircle (generic function with 1 method)
julia> areaofcircle()
What's the radius?
42
a circle with radius 42.0 has an area of:
5541.769440932395
julia>
這在 Julia REPL 會話中有效;當呼叫時,該函式會等待使用者在鍵盤上鍵入字串並按回車/Enter 鍵。
