Ruby 字串(String)


Ruby 中的 String 物件用於儲存或操作一個或多個位元組的序列。

Ruby 字串分為單引號字串(')和雙引號字串("),區別在於雙引號字串能夠支援更多的轉義字元。

單引號字串

最簡單的字串是單引號字串,即在單引號內存放字串:

'这是一个 Ruby 程序的字符串'

如果您需要在單引號字串內使用單引號字符,那麼需要在單引號字串使用反斜線(\),這樣Ruby 解釋器就不會認為這個單引號字元是字串的終止符號:

'Won\'t you read O\'Reilly\'s book?'

反斜線也能轉義另一個反斜杠,這樣第二個反斜杠本身不會解釋為轉義字元。 #在雙引號字串中我們可以使用

#{}

井號和大括號來計算表達式的值:

字串中嵌入變數:

#!/usr/bin/ruby
# -*- coding: UTF-8 -*-

name1 = "Joe"
name2 = "Mary"
puts "你好 #{name1},  #{name2} 在哪?"

以上實例輸出運行輸出結果為:

你好 Joe,  Mary 在哪?

字串中進行數學運算:

#!/usr/bin/ruby
# -*- coding: UTF-8 -*-

x, y, z = 12, 36, 72
puts "x 的值为 #{ x }"
puts "x + y 的值为 #{ x + y }"
puts "x + y + z 的平均值为 #{ (x + y + z)/3 }"

以上實例輸出運行輸出結果為:

x 的值为 12
x + y 的值为 48
x + y + z 的平均值为 40

Ruby 中也支援一種採用%q 和%Q 來引導的字串變量,%q 使用的是單引號引用規則,而%Q 是雙引號引用規則,後面再接一個(! [ { 等等的開始界定符和與} ] ) 等等的末尾界定符。非字母數字的單字元.如:[,{,(,<,!等,字串會一直讀取到發現相符的結束符號為止.

#!/usr/bin/ruby
# -*- coding: UTF-8 -*-

desc1 = %Q{Ruby 的字符串可以使用 '' 和 ""。}
desc2 = %q|Ruby 的字符串可以使用 '' 和 ""。|

puts desc1
puts desc2

以上實例輸出運行輸出結果為:

Ruby 的字符串可以使用 '' 和 ""。
Ruby 的字符串可以使用 '' 和 ""。

轉義字元

下標列出了可使用反斜線符號轉義的轉義字元或非列印字元。


注意:

在一個雙引號括起的字串內,轉義字元會被解析。 ,原樣輸出。

##\a0x07警報符號\b0x08退格鍵#\cx Control-x#\C-x \e\f\M-\C-x \n#\nnn\r##\s0x20空格符號\t0x09製表符\v0x0b垂直製表符\x##  #字元編碼
反斜線符號十六進位字元#描述
##Control-x
0x1b轉義符號
0x0c#換頁符號
 Meta-Control-x
0x0a換行符號
 八進位表示法,其中n 的範圍為0.7
0x0d回車符號
字元x\xnn
十六進位表示法,其中n 的範圍為0.9、 a.f 或A.F
Ruby 的預設字元集是ASCII,字元可用單一位元組表示。如果您使用 UTF-8 或其他現代的字元集,字元可能是用一個到四個位元組表示。

您可以在程式開頭使用 $KCODE 來改變字元集,如下所示:

$KCODE = 'u'

下面是 $KCODE 可能的值。

編碼描述ASCII (與 none 相同)。這是預設的。 EUC。 None (與 ASCII 相同)。 UTF-8。
#a
e
n
u

字串內建方法

我們需要有一個 String 物件的實例來呼叫 String 方法。以下是建立 String 物件實例的方式:

new [String.new(str="")]

這將傳回一個包含 str 副本的新的字串物件。現在,使用 str 對象,我們可以呼叫任意可用的實例方法。例如:

#!/usr/bin/ruby

myStr = String.new("THIS IS TEST")
foo = myStr.downcase

puts "#{foo}"

這將產生以下結果:

this is test

下面是公共的字串方法(假設 str 是一個 String 物件):

序號方法& 描述
#1str % arg
使用格式規格格式化字串。如果 arg 包含一個以上的替代,那麼 arg 必須是陣列。如需了解更多格式規範的信息,請查看"內核模組"下的 sprintf。
2str * integer
#傳回一個包含 integer 個 str 的新的字串。換句話說,str 被重複了 integer 次。
3str + other_str
連接 other_str 到 str。
4str << obj
連接一個物件到字串。如果物件是範圍為 0.255 之間的固定數字 Fixnum,則它會轉換為一個字元。把它與 concat 比較。
5str <=> other_str
把str 與other_str 比較,回傳-1(小於)、0 (等於)或1(大於)。比較是區分大小寫的。
6str == obj
檢查 str 和 obj 的相等性。如果 obj 不是字串,則傳回 false,如果 str <=> obj,則傳回 true,傳回 0。
7str =~ obj
根據正規表示式模式 obj 匹配 str。傳回符合開始的位置,否則傳回 false。
8 
 
9 str.capitalize
把字串轉換成大寫字母顯示。
10str.capitalize!
與 capitalize 相同,但是 str 會變更並傳回。
11str.casecmp
不區分大小寫的字串比較。
12str.center
#居中字串。
13str.chomp
#從字串結尾移除記錄分隔符號($/),通常是 \n。如果沒有記錄分隔符,則不進行任何操作。
14str.chomp!
#與 chomp 相同,但 str 會變更並傳回。
15str.chop
移除 str 中的最後一個字元。
16str.chop!
#與 chop 相同,但 str 會變更並傳回。
17str.concat(other_str)
連接 other_str 到 str。
18str.count(str, ...)
給一個或多個字元集計數。如果有多個字元集,則給這些集合的交集計數。
19str.crypt(other_str)
對 str 套用單向加密雜湊。參數是兩個字元長的字串,每個字元的範圍為 a.z、 A.Z、 0.9、 . 或 /。
20str.delete(other_str, ...)
#傳回 str 的副本,參數交集中的所有字元會被刪除。
21str.delete!(other_str, ...)
與delete 相同,但是str 會改變並傳回。
22str.downcase
傳回 str 的副本,所有的大寫字母會被替換為小寫字母。
23str.downcase!
與 downcase 相同,但 str 會變更並回傳。
24str.dump
#回傳str 的版本,所有的非列印字元被替換為\nnn 符號,所有的特殊字符被轉義。
25str.each(separator=$/) { |substr| block }
使用參數作為記錄分隔符號(預設是$/)分隔str,傳遞每個子字串給被提供的區塊。
26str.each_byte { |fixnum| block }
傳遞str 的每個位元組給block,以位元組的十進位表示法傳回每個位元組。
27str.each_line(separator=$/) { |substr| block }
使用參數作為記錄分隔符號(預設是$/)分隔str,傳遞每個子字串給被提供的block。
28str.empty?
如果 str 為空(即長度為 0),則傳回 true。
29str.eql?(other)
如果兩個字串有相同的長度和內容,則這兩個字串相等。
30str.gsub(pattern, replacement) [or]
str.gsub(pattern) { |match| block }

傳回str 的副本,pattern 的所有出現都會被替換為replacement 或block 的值。 pattern 通常是一個正規表示式Regexp;如果是一個字串String,則沒有正規表示式元字元被解釋(即,/\d/ 將匹配一個數字,但'\d' 將匹配一個反斜線後跟一個'd')。
31str[fixnum] [or] str[fixnum,fixnum] [or] str[range] [or] str[regexp] [或] str[regexp, fixnum] [or] str[other_str]
使用下列的參數引用str:參數為一個Fixnum,則傳回fixnum 的字元編碼;參數為兩個Fixnum,則傳回一個從偏移(第一個fixnum)開始截至長度(第二個fixnum)為止的子字串;參數為range,則傳回該範圍內的一個子字串;參數為regexp,則傳回符合字串的部分;參數為帶有fixnum 的regexp,則傳回fixnum 位置的符合資料;參數為other_str,則傳回符合other_str 的子字串。一個負數的 Fixnum 從字串的末尾 -1 開始。
32str[fixnum] = fixnum [or] str[fixnum] = new_str [or] str[fixnum, fixnum] = new_str [or ] str[range] = aString [or] str[regexp] =new_str [or] str[regexp, fixnum] =new_str [or] str[other_str] = new_str ]
#替換整個字串或部分字串。與 slice! 同義。
33str.gsub!(pattern, replacement) [or] str.gsub!(pattern) { |match| block }
執行String#gsub 的替換,傳回str,如果沒有替換執行則傳回nil。
34str.hash
#傳回一個基於字串長度和內容的雜湊。
35str.hex
#把str 的前導字元當作十六進位數字的字串(一個可選的符號和一個可選的0x),並傳回相對應的數字。如果錯誤則傳回零。
36str.include? other_str [or] str.include? fixnum
如果str 包含給定的字串或字符,則傳回true。
37str.index(substring [, offset]) [or]
str.index(fixnum [, offset]) [or ]
str.index(regexp [, offset])

傳回給定子字串、字元(fixnum)或模式(regexp)在str 中第一次出現的索引。如果未找到則傳回 nil。如果提供了第二個參數,則指定在字串中開始搜尋的位置。
38str.insert(index, other_str)
在給定索引的字元前插入 other_str,修改 str。負值索引從字串的末尾開始計數,並在給定字元後插入。其意圖是在給定的索引處開始插入字串。
39str.inspect
傳回 str 的可列印版本,帶有轉義的特殊字元。
40str.intern [or] str.to_sym
傳回與str 對應的符號,如果之前不存在,則建立符號。
41str.length
傳回 str 的長度。把它與 size 比較。
42str.ljust(integer, padstr=' ')
如果integer 大於str 的長度,則傳回長度為integer 的新字串,新字串以str 左對齊,並以padstr 作為填充。否則,返回 str。
43str.lstrip
傳回 str 的副本,移除了前導的空格。
44str.lstrip!
從 str 移除前導的空格,如果沒有變更則傳回 nil。
45str.match(pattern)
如果pattern 不是正規表示式,則把pattern 轉換為正規表示式Regexp ,然後在str 上呼叫它的匹配方法。
46str.oct
#把str 的前導字元當作十進位數字的字串(一個可選的符號) ,並傳回相對應的數字。如果轉換失敗,則傳回 0。
47str.replace(other_str)
把 str 中的內容替換為 other_str 中的對應的值。
48str.reverse
#傳回一個新字串,新字串是 str 的倒序。
49str.reverse!
逆轉 str,str 會改變並回傳。
50str.rindex(substring [, fixnum]) [or]
str.rindex(fixnum [, fixnum]) [or ]
str.rindex(regexp [, fixnum])

傳回給定子字串、字元(fixnum)或模式(regexp)在str 中最後一次出現的索引。如果未找到則傳回 nil。如果提供了第二個參數,則指定在字串中結束搜尋的位置。超出該點的字元將不被考慮。
51str.rjust(integer, padstr=' ')
如果integer 大於str 的長度,則傳回長度為integer 的新字串,新字串以str 右對齊,並以padstr 作為填充。否則,返回 str。
52str.rstrip
傳回 str 的副本,移除了尾隨的空格。
53str.rstrip!
從 str 移除尾隨的空格,如果沒有變更則傳回 nil。
54str.scan(pattern) [or]
str.scan(pattern) { |match, ...| block }

兩種形式符合pattern(可以是一個正規表示式Regexp 或一個字串String)遍歷str。針對每個匹配,會產生一個結果,結果會加到結果陣列或傳遞給 block。如果 pattern 不包含分組,則每個獨立的結果由符合的字串、$& 組成。如果 pattern 包含分組,則每個獨立的結果是包含每個分組入口的陣列。
55str.slice(fixnum) [or] str.slice(fixnum, fixnum) [or]
str.slice(range ) [or] str.slice(regexp) [or]
str.slice(regexp, fixnum) [or] str.slice(other_str)
See str[fixnum], etc.
str.slice !(fixnum) [或] str.slice!(fixnum, fixnum) [或] str.slice!(range) [or] str.slice!(regexp) [or] str.slice!(other_str)

從 str 中刪除指定的部分,並傳回刪除的部分。如果值超出範圍,參數帶有 Fixnum 的形式,將產生一個 IndexError。參數為 range 的形式,將產生一個 RangeError,參數為 Regexp 和 String 的形式,將忽略執行動作。
56str.split(pattern=$;, [limit])

基於分隔符,把str分成子字串,並傳回這些子字串的陣列。

如果 pattern 是一個字串 String,那麼在分割 str 時,它將作為分隔符號使用。如果 pattern 是單一的空格,那麼 str 是基於空格進行分割,會忽略前導空格和連續空格字元。

pattern  是正規表示式 Regexp,則 str 在 pattern 符合的地方被分割。當 pattern 匹配一個玲長度的字串時,str 被分割成單一字元。

如果省略了 pattern 參數,則使用 $; 的值。如果 $; 為 nil(預設的),str 是基於空格進行分割,就像是指定了 ` ` 作為分隔符號一樣。

如果省略了 limit 參數,會抑制尾隨的 null 欄位。如果 limit 是正數,則最多會傳回該數量的欄位(如果 limit 為 1,則會傳回整個字串作為陣列中的唯一入口)。如果 limit 是負數,則傳回的欄位數量不限制,且不抑制尾隨的 null 欄位。

57str.squeeze([other_str]*)
使用String#count 所描述的程式從other_str 參數建立一系列字元。傳回一個新的字串,其中集合中出現的相同的字元會被替換為單一字元。如果沒有給出參數,則所有相同的字元都被替換為單一字元。
58str.squeeze!([other_str]*)
與squeeze 相同,但是str 會發生變化並返回,如果沒有變化則傳回nil。
59str.strip
返回 str 的副本,移除了前導的空格和尾隨的空格。
60str.strip!
從str 中移除前導的空格和尾隨的空格,如果沒有變更則傳回nil。
61str.sub(pattern, replacement) [or]
str.sub(pattern) { |match| block }

傳回str 的副本,pattern 的第一次出現會被替換為replacement 或block 的值。 pattern 通常是正規表示式 Regexp;如果是一個字串 String,則沒有正規表示式元字元被解釋。
62str.sub!(pattern, replacement) [or]
str.sub!(pattern) { |match| block }

執行String#sub 替換,並傳回str,如果沒有替換執行,則傳回nil。
63str.succ [or] str.next
傳回 str 的繼承。
64str.succ! [or] str.next!
相當於String#succ,但str 會改變並返回。
65str.sum(n=16)
傳回str 中字元的n-bit 校驗和,其中n是可選的Fixnum 參數,預設為16。結果是簡單地把 str 中每個字元的二進位值的總和,以 2n - 1 為模。這不是一個特別好的校驗和。
66str.swapcase
回傳str 的副本,所有的大寫字母轉換為小寫字母,所有的小寫字母轉換為大寫字母。
67str.swapcase!
相當於String#swapcase,但是str 會發生變化並返回,如果沒有變化則返回nil。
68str.to_f
傳回把 str 中的前導字元解釋為浮點數的結果。超出有效數字的末尾的多餘字元會被忽略。如果在 str 的開頭沒有有效數字,則傳回 0.0。此方法不會產生異常。
69str.to_i(base=10)
返回把str 中的前導字元解釋為整數基數(基數為2、 8、 10 或16)的結果。超出有效數字的末尾的多餘字元會被忽略。如果在 str 的開頭沒有有效數字,則傳回 0。此方法不會產生異常。
70str.to_s [or] str.to_str
傳回接收的值。
71str.tr(from_str, to_str)
#傳回 str 的副本,把 from_str 中的字元替換為 to_str 中相對應的字元。如果 to_str 比 from_str 短,那麼它會以最後一個字元進行填充。兩個字串都可以使用 c1.c2 符號表示字元的範圍。如果 from_str 以 ^ 開頭,則表示除了所列出的字元以外的所有字元。
72str.tr!(from_str, to_str)
相當於String#tr,但str 會改變並傳回,如果沒有變化則回傳nil。
73str.tr_s(from_str, to_str)
把str 依照String#tr 所描述的規則處理,然後移除會影響翻譯的重複字元。
74str.tr_s!(from_str, to_str)
相當於String#tr_s,但str 會變更並傳回,如果沒有變化則回傳nil。
75str.unpack(format)
根據format 字串解碼str(可能包含二進位資料),回傳被擷取的每個值的數組。 format 字元由一系列單字元指令組成。每個指令後可以跟著一個數字,表示重複指令的次數。星號(*)將使用所有剩餘的元素。指令 sSiIlL 每個後可能都會跟著一個底線(_),為指定類型使用底層平台的本地尺寸大小,否則使用獨立於平台的一致的尺寸大小。 format 字串中的空格會被忽略。
76str.upcase
傳回 str 的副本,所有的小寫字母都會被替換為大寫字母。操作是環境不敏感的,只有字元 a 到 z 會受影響。
77str.upcase!
改變 str 的內容為大寫,如果沒有變更則傳回 nil。
78str.upto(other_str) { |s| block }
遍歷連續值,以str 開始,以other_str結束(包含),輪流傳遞每個值給block。 String#succ 方法用於產生每個值。

字串 unpack 指令

下表列出了方法 String#unpack 的解壓縮指令。

##String移除尾隨的null 和空格。 aString字串。 BString從每個字元中提取位元(首先是最高有效位元)。 bString從每個字元中提取位元(首先是最低有效位元)。 CFixnum擷取一個字元作為無符號整數。 cFixnum提取一個字元作為整數。 D, dFloat把 sizeof(double) 長度的字元當作原生的 double。 EFloat把 sizeof(double) 長度的字元當作 littleendian 位元組順序的 double。 eFloat把 sizeof(float) 長度的字元當作 littleendian 位元組順序的 float。 F, fFloat把 sizeof(float) 長度的字元當作原生的 float。 GFloat把 sizeof(double) 長度的字元當作 network 位元組順序的 double。 gFloat把 sizeof(float) 長度的字元當作 network 位元組順序的 float。 HString從每個字元中提取十六進位(首先是最高有效位元)。 hString從每個字元中提取十六進位(首先是最低有效位元)。 IInteger把 sizeof(int) 長度(透過 _ 修改)的連續字元當作原生的 integer。 iInteger把 sizeof(int) 長度(透過 _ 修改)的連續字元當作有符號的原生的 integer。 LInteger把四個(透過 _ 修改)連續字元當作無符號的原生的 long integer。 lInteger把四個(透過 _ 修改)連續字元當作有符號的原生的 long integer。 MString引用可列印的。 mStringBase64 編碼。 NInteger把四個字元當作 network 位元組順序的無符號的 long。 nFixnum把兩個字元當作 network 位元組順序的無符號的 short。 PString把sizeof(char *) 長度的字元當作指針,並從引用的位置返回\emph{len}字元。 pString把 sizeof(char *) 長度的字元當作一個空結束字元的指標。 QInteger把八個字元當作無符號的 quad word(64 位元)。 qInteger
指令回傳描述
AString
#A
###把八個字元當作有符號的 quad word(64 位元)。 ############S######Fixnum######把兩個(如果使用 _ 則不同)連續字元當作 native 位元組順序的無符號的 short。
sFixnum把兩個(如果使用 _ 則不同)連續字元當作 native 位元組順序的有符號的 short。
UIntegerUTF-8 字符,作為無符號整數。
uStringUU 編碼。
VFixnum把四個字元當作 little-endian 位元組順序的無符號的 long。
vFixnum把兩個字元當作 little-endian 位元組順序的無符號的 short。
wIntegerBER 壓縮的整數。
X 向後跳過一個字元。
x 向前跳過一個字元。
ZString和 * 一起使用,移除尾隨的 null 直到第一個 null。
@ 跳過 length 參數給定的偏移量。

實例

嘗試下面的實例,解壓縮各種資料。

"abc rrreeerrreeeabc rrreeerrreee".unpack('A6Z6')   #=> ["abc", "abc "]
"abc rrreeerrreee".unpack('a3a3')           #=> ["abc", " rrreee0rrreee0"]
"abc rrreeeabc rrreee".unpack('Z*Z*')       #=> ["abc ", "abc "]
"aa".unpack('b8B8')                 #=> ["10000110", "01100001"]
"aaa".unpack('h2H2c')               #=> ["16", "61", 97]
"\xfe\xff\xfe\xff".unpack('sS')     #=> [-2, 65534]
"now=20is".unpack('M*')             #=> ["now is"]
"whole".unpack('xax2aX2aX1aX2a')    #=> ["h", "e", "l", "l", "o"]