Julia 数组操作:向量、矩阵、多维数组
Julia 的数组核心在于 Array 类型,它是数据存储和计算的基础。无论是处理只有一列的向量、二维的表格矩阵,还是更高维度的数据块,掌握数组的创建、变形与运算规则是高效编程的关键。
一、 创建基础数组:向量与矩阵
Julia 创建数组最直接的方式是使用方括号 []。元素之间的分隔符决定了数组的维度和形状。
1. 创建向量(一维数组)
在方括号内输入元素,使用逗号分隔。这种方式生成的数组在数学上被视为列向量。
v = [1, 2, 3, 4]
若要创建行向量,使用空格分隔元素。
v_row = [1 2 3 4]
2. 创建矩阵(二维数组)
在构建矩阵时,使用空格分隔同一行的元素,使用分号 ; 换行或直接回车分隔不同的行。
# 使用分号换行
m1 = [1 2 3; 4 5 6]
# 使用回车换行(更直观,适合复制粘贴数据)
m2 = [10 20 30
40 50 60]
3. 指定元素类型
默认情况下,Julia 会根据输入值自动推断类型。若为了性能优化,可以在方括号前声明类型。
# 声明一个 Float64 类型的空数组
float_arr = Float64[]
# 声明一个 Int32 类型的矩阵
int_matrix = Int32[1 2; 3 4]
二、 快速初始化数组
手动输入元素仅适用于小规模数据。对于大规模或特定格式的数组,使用初始化函数。
1. 创建未初始化数组
使用 Array 或 Vector/Matrix 构造函数,配合 undef 关键字。这会分配内存但不填充具体值,速度最快,但读取内容前必须先赋值。
# 创建一个包含 100 个未初始化元素的 Vector
uninit_vec = Vector{Float64}(undef, 100)
# 创建一个 3x3 的未初始化 Matrix
uninit_mat = Matrix{Int64}(undef, 3, 3)
2. 创建填充数组
使用 zeros, ones, fill 函数快速生成特定值的数组。
# 创建全 0 矩阵
z = zeros(3, 3)
# 创建全 1 向量
o = ones(5)
# 填充特定值(例如 7.5)
f = fill(7.5, (2, 4)) # 2行4列
3. 创建随机数组
利用 rand 和 randn 生成随机数。rand 生成均匀分布数(0到1之间),randn 生成标准正态分布数。
# 生成 2x2 的均匀分布随机矩阵
r1 = rand(2, 2)
# 生成 2x2 的正态分布随机矩阵
r2 = randn(2, 2)
三、 索引与切片操作
获取数组中的特定元素或子集是日常操作中最频繁的步骤。
1. 基础索引
Julia 的索引从 1 开始。使用 end 代表最后一个元素。
arr = [10, 20, 30, 40, 50]
# 获取第一个元素
first_val = arr[1]
# 获取最后一个元素
last_val = arr[end]
对于矩阵,使用 [行, 列] 的格式。
mat = [1 2 3; 4 5 6]
# 获取第 1 行第 2 列的元素(值为 2)
val = mat[1, 2]
2. 范围切片
使用冒号 start:step:stop 语法提取连续或不连续的子集。如果步长为 1,可以简写为 start:stop。
vec = 1:10
collect(vec) # 将范围转为数组以便展示
# 提取前 3 个元素
sub1 = vec[1:3]
# 提取奇数位置的元素(步长为 2)
sub2 = vec[1:2:end]
# 提取第 3 到倒数第 2 个元素
sub3 = vec[3:end-1]
对于矩阵,可以提取整行或整列。
m = [1 2 3; 4 5 6; 7 8 9]
# 提取第 2 行(所有列)
row_2 = m[2, :]
# 提取第 3 列(所有行)
col_3 = m[:, 3]
四、 广播机制
“广播”是 Julia 处理数组运算的核心机制,它允许将函数和运算符应用到数组的每一个元素上,而无需编写显式的循环。
1. 逐元素运算
当需要对数组中的每个元素进行加减乘除或函数运算时,在运算符或函数名后添加点 . 号。
A = [1, 2, 3]
# 数组与标量相乘(无需加点,Julia 自动处理部分场景,但加点更通用)
B = A .* 2
# 数组与数组逐元素相乘
C = [2, 3, 4]
D = A .* C # 对应位置相乘:[2, 6, 12]
# 对每个元素开根号
E = sqrt.(A)
2. 广播函数
自定义函数或标准库函数均可通过加点 . 进行广播。
# 定义一个简单的函数
f(x) = x^2 + 2x
# 对整个数组进行广播计算
result = f.([1, 2, 3])
五、 数组变形与拼接
处理数据时,经常需要改变数组的形状或将多个数组合并。
1. 变形
使用 reshape 函数改变数组的维度,前提是新维度的元素总数必须与原数组一致。
# 创建一个 1到6 的向量
v = 1:6
collect(v)
# 将其变形为 2x3 的矩阵
m = reshape(v, (2, 3))
# 结果为:
# 1 3 5
# 2 4 6
为了更直观地理解数据在内存中的顺序与 reshape 的关系,请参考以下逻辑:
2. 拼接
使用括号 [] 配合空格或逗号进行拼接,或者使用专门的函数 hcat (水平拼接), vcat (垂直拼接), cat (指定维度拼接)。
| 操作 | 语法示例 | 说明 |
|---|---|---|
| 垂直拼接 | [a; b] 或 vcat(a, b) |
增加行数,列数需一致 |
| 水平拼接 | [a b] 或 hcat(a, b) |
增加列数,行数需一致 |
| 深度拼接 | cat(a, b, dims=3) |
沿指定维度拼接(如构建 3D 数组) |
a = [1 2]
b = [3 4]
# 垂直拼接 -> 2x2 矩阵
v_res = [a; b]
# 水平拼接 -> 1x4 矩阵
h_res = [a b]
六、 多维数组
Julia 并不局限于二维数组,它可以轻松处理任意维度的数据。在图像处理(3D:宽x高x通道)或科学计算中非常常见。
1. 创建多维数组
初始化函数(如 zeros, rand)接受多个参数来定义维度。
# 创建一个 3x3x3 的三维数组(3层,每层3行3列)
arr_3d = zeros(3, 3, 3)
# 创建一个 2x2x2x2 的四维数组
arr_4d = ones(2, 2, 2, 2)
2. 索引多维数组
索引时,依次提供每个维度的坐标。
# 假设 arr_3d 尺寸为 (3, 3, 3)
# 获取第 1 层,第 2 行,第 3 列的元素
val = arr_3d[1, 2, 3]
# 获取第 2 层的所有数据(返回一个 3x3 的矩阵)
layer_2 = arr_3d[:, :, 2]
# 获取所有层的第 1 行第 1 列(返回一个长度为 3 的向量)
corner = arr_3d[1, 1, :]
3. 维度变换
使用 dropdims 或 squeeze (旧版本) 去除长度为 1 的维度。使用 permutedims 交换维度顺序。
x = zeros(2, 1, 3) # 形状为 2x1x3
# 去掉长度为 1 的第 2 维,变为 2x3
y = dropdims(x; dims=2)
# 交换维度,例如将 RGB 图像通道从第 3 维移到第 1 维
# 假设 img 为 3x3x3 (HxWxC)
img_transposed = permutedims(img, (3, 1, 2)) # 变为 CxHxW
暂无评论,快来抢沙发吧!