# Ruby 学习笔记
## 1、简介
1. 定义:一种简单快捷的面向对象脚本语言
2. 开发者:松本行弘
3. 开发时间:1995年
4. 设计目的:A PROGRAMMER'S BEST FRIEND【程序员的最佳朋友】
5. 文件扩展名:rb
## 2、语言特性
1. 真正的面向对象编程语言
2. 可扩展性强,且易于维护
3. 丰富的语法糖,程序员友好
## 3、应用场景
1. 网站开发
2. 脚本编程
## 4、Ruby 注释
1. 单行注释 ` # 注释 Ruby 单行注释 `
2. 多行注释
```ruby
=begin
这是多行注释
=end
```
## 5、Ruby 文件的构造与析构语句
### 1. 文件构造语句
```ruby
BEGIN {
puts '这是 Ruby 文件的运行之前调用'
}
```
### 2. 文件析构语句
```ruby
END {
puts '这是 Ruby 文件的运行之后调用'
}
```
## 6、Ruby 变量
1. 变量不能使用保留字,命名规则:小写字母
2. 变量名只能由[a-z_0-1]组成,且只能由字母开头
3. 使用 ` .class ` 可以获取数据的类型
```ruby
variable='' # 声明变量
puts variable.class # String【Integer、Float、String、Array、Hash、NilClass、TrueClass、FalseClass】
```
## 7、Ruby 数据类型
### 1. 数值类型 Number
#### 1、整型 Integer
#### 2、浮点型 Float
### 2. 字符串类型 String
1. 声明字符串
```ruby
var_string = '声明单行字符串'
var_string = "#{var_string},双引号中可以解析变量"
puts var_string
```
2. 多行字符串 Here Document
```ruby
var_string = 'Here Document 中仅仅使用EOF可以解析变量'
here_document = <<EOF
这是多行字符串声明方法
#{var_string}
EOF
puts here_document
```
3. 多行字符串 Here Document 不解析字符串方法
```ruby
var_string = '使用 \'EOF\' Here Documnet 不解析变量'
here_document = <<'EOF'
使用 'EOF' Here Documnet 不解析变量
#{var_string}
#{任意的 Ruby 表达式}
EOF
puts here_document
```
4. 拼接字符串使用 ` + `
### 3. 布尔类型 Boolean
1. 真 true
2. 假 false
### 4. 数组 Array
- Ruby 数组可以看作一种索引数组
#### 1、声明数组
```ruby
# 定义一个空数组
var_array = []
## 添加值
var_array[1] = 'a'
## 获取数组长度
var_array_length = var_array.length
puts "数组的长度 length 为:#{var_array_length}" # 2
## 定义一个长度为 n=10 的数组
n = 10
var_array = Array.new(n)
puts "数组的长度为:#{var_array.length}"
```
#### 2、数组简单操作
##### 1. 向数组中添加一个值[添加元素到数组结尾]
```ruby
# var_array.push(10);
var_array << 10;
puts "添加元素到数组结尾后的额数组长度为:#{var_array.length}" # 11
```
##### 2. 删除数组某一个值
```ruby
var_array.delete_at(9);
puts "删除数组某一个值后的数组长度为:#{var_array.length}" # 10
```
##### 3. 移除数组第一个值
```ruby
var_array.delete_at(0);
puts "移除数组第一个值后的额数组长度为:#{var_array.length}" # 9
var_array_first_value = var_array.shift()
puts "移除数组第一个值后的额数组长度为:#{var_array.length}" # 8
```
##### 4. 移除数组最后一个值
```ruby
var_array_last_value = var_array.pop();
puts "删除数组最后一个值为:#{var_array_last_value}" # 10
```
##### 5. 添加元素到数组开头
```ruby
var_array = [0].concat(var_array)
puts var_array.inspect # [0, nil, nil, nil, nil, nil, nil, nil]
```
##### 6. 数组迭代
```ruby
## 1. 键值迭代
var_array.each_with_index do |value,key|
var_array[key] = value.nil? ? key : value
end
puts var_array.inspect # [0, 1, 2, 3, 4, 5, 6, 7]
```
```ruby
## 2. 只能迭代出值
var_array.each do |value|
puts "current item is #{value}"
end
```
##### 7. 数组克隆【Ruby 中数组为对象,所以赋值为引用赋值,所以当需要复制数组时,需要克隆复制】
```ruby
var_array2 = var_array
puts var_array2.inspect # [0, 1, 2, 3, 4, 5, 6, 7]
var_array << 10
puts var_array2.inspect # [0, 1, 2, 3, 4, 5, 6, 7, 10]
var_array3 = var_array.clone
puts var_array3.inspect # [0, 1, 2, 3, 4, 5, 6, 7, 10]
var_array << 100
puts var_array3.inspect # [0, 1, 2, 3, 4, 5, 6, 7, 10]
puts var_array.inspect # [0, 1, 2, 3, 4, 5, 6, 7, 10, 100]
```
### 5. 哈希 Hash
- 哈希可以看作一种关联数组
#### 1、声明哈希
```ruby
# 定义一个空哈希
var_hash = {}
puts var_hash # {}
```
#### 2. 获取哈希长度
```ruby
puts "哈希的长度为:#{var_hash.length}" # 1
```
#### 3. 哈希简单操作
##### 1. 向哈希中添加一个值[添加元素到哈希结尾]
```ruby
var_hash[:descript] = '描述'
```
##### 2. 删除哈希某一个值
```ruby
var_hash.delete(:descript)
puts var_hash # {:title=>"标题"}
```
##### 3. 移除哈希第一个值
```ruby
var_hash[:descript] = '移除哈希第一个值'
puts var_hash # {:title=>"标题", :descript=>"移除哈希第一个值"}
var_hash_first_value = var_hash.shift(); # 返回 [键,值] 或者 键,值
puts var_hash # {:descript=>"移除哈希第一个值"}
puts var_hash_first_value.inspect
```
##### 4. 移除哈希最后一个值
##### 5. 添加元素到哈希开头
##### 6. 哈希迭代
```ruby
var_hash = {}
var_hash[:title] = 'hash.each'
var_hash[:descript] = '哈希迭代'
var_hash.each do |key,value|
puts "current #{key} is #{value}"
end
```
### 6. Ruby 中类和对象
#### 1、类的组成
- 类名称命名规则:使用大驼峰命名法
##### 1. 属性
1. 静态属性:即类属性,使用 ` @@ ` 声明,子类与父类共同调用
2. 常量属性:使用大写字母声明,子类与父类共同调用,一般不需更改
3. 实例属性:使用 ` @ ` 声明
##### 2. 方法 使用 ` def ` 定义
1. 静态方法
2. 实例方法
- 方法的最外层小括号 ` () ` 可以省略
- 每个方法最后一行默认是返回值,不需要写 ` return `
##### 3. 普通变量
- 变量是在方法中定义的局部变量,只能在方法中被调用
##### 4. 代码示例
```ruby
class Language
# 构造方法
def initialize
puts '实例化了一个类'
end
# 常量属性,命名规则:大写字母
TITLE = '语言'
# 静态属性
@@description = '学习语言的特性'
# 实例属性
@name='Ruby'
# 静态方法
def self.get_desc
@@description
end
# 实例方法
def set_name(name)
@name=name
end
def get_name
@name
end
end
## 1、实例化一个类
language = Language.new
## 2、调用常量属性
result = Language::TITLE
puts "调用常量属性结果为:#{result}"
## 3、调用静态属性:无法直接调用静态属性
# result = Language.description # 报错
## 4、调用静态方法
result = Language.get_desc
puts "调用静态方法结果为:#{result}"
## 5、调用实例属性:无法直接调用实例属性
# result = language.name # 报错
## 6、调用实例方法
language.set_name('PHP')
result = language.get_name
puts "调用实例方法后输出实例属性为:#{result}"
```
#### 2、继承
1. 使用关键字符 ` < `
#### 3、访问控制
##### 1. attr_accessor 控制属性
1. attr_accessor 关键字:相当于 attr_reader 和 attr_writer
2. 使用方法:` attr_accessor :variable_name ` 相当于定义了 ` variable_name() ` 获取方法与 ` variable_name=() ` 设置方法
##### 2. 3P 访问控制方法
- Ruby 不在实例和类变量上应用任何访问控制
1. public:默认控制,可被任意对象调用
2. protected:保护方法,外部无法访问,只能在类以及子类的内部访问
3. private:私有保护,只能在类的内部使用,且子类无法访问、但可以重新声明
#### 注意
1. 不通过构造方法给实例属性赋于的初值是无效的
2. Ruby 中无法直接调用类和对象的*非常量属性*
### 备注
#### 1、Ruby 中 Array数组 与 Hash字典 的区别
1. 数组定义时,[索引、键]由系统生成,与 C 语言一致
2. 字典声明时必须指定键,否则报错,并且一般不能是数字
3. 数组的索引无明显意义,如果需要[索引、键],则使用字�