find 是 MATLAB 中一个非常基础且极其有用的函数,它的主要作用是定位数组中非零元素(或满足特定条件的元素)的索引。

核心语法与基本用法
find 函数最常用的形式有以下几种:
语法 1: 单个输出参数 - 返回线性索引
index = find(A)
-
功能: 找出矩阵
A中所有非零元素的位置,并将这些位置的线性索引存入列向量index中。 -
什么是线性索引? 在 MATLAB 中,矩阵是按列存储的,线性索引就是将矩阵的所有元素排成一列后,每个元素对应的序号,对于一个 2x3 的矩阵
A:A = [1, 2, 3; 4, 5, 6]元素
1的线性索引是1,2是2,3是3,4是4,依此类推。
(图片来源网络,侵删) -
示例:
A = [0, 5, 0; 9, 0, 2]; indices = find(A); disp(indices);输出:
2 4 6解释:矩阵
A中非零元素是5(位置 (1,2))、9(位置 (2,1)) 和2(位置 (2,3)),它们对应的线性索引分别是2、4、6。
语法 2: 两个输出参数 - 返回行和列索引
[row, col] = find(A)
-
功能: 找出矩阵
A中所有非零元素的位置,并将它们的行索引存入row,列索引存入col。row和col都是列向量,且长度相同。 -
示例:
A = [0, 5, 0; 9, 0, 2]; [rows, cols] = find(A); disp('行索引:'); disp(rows); disp('列索引:'); disp(cols);输出:
行索引: 2 1 2 列索引: 1 2 3解释:第一个非零元素
9在第 2 行第 1 列;第二个非零元素5在第 1 行第 2 列;第三个非零元素2在第 2 行第 3 列。
语法 3: 带有条件判断
这是 find 最强大的功能之一,可以用来查找满足特定条件的元素。
index = find(A, condition, value) [row, col] = find(A, condition, value)
-
condition: 可以是'>','>=','<','<=', , 。 -
value: 与condition配合使用的数值。 -
示例 1: 找出大于 5 的元素
A = [1, 8, 3; 9, 2, 6]; % 找出大于 5 的元素的线性索引 indices = find(A > 5); disp(indices); % 输出 2 4 6 (对应 8, 9, 6) % 找出大于 5 的元素的行列索引 [rows, cols] = find(A > 5); disp('行:'); disp(rows); % 输出 1 2 1 disp('列:'); disp(cols); % 输出 2 1 3 -
示例 2: 找出等于特定值的元素
B = [1, 2, 2, 3, 2]; % 找出所有等于 2 的元素的索引 indices_of_2 = find(B == 2); disp(indices_of_2); % 输出 2 3 5
语法 4: 查找前 N 个或后 N 个匹配项
[rows, cols] = find(A, k) [rows, cols] = find(A, k, 'first') [rows, cols] = find(A, k, 'last')
-
k: 一个整数,指定要查找的元素数量。 -
'first': 默认选项,查找前k个满足条件的元素(按列优先顺序)。 -
'last': 查找最后k个满足条件的元素。 -
示例:
A = [1, 8, 3; 9, 2, 6]; % 找出前 2 个大于 5 的元素 [rows_first, cols_first] = find(A > 5, 2, 'first'); disp('前2个:'); disp([rows_first, cols_first]); % 输出 1 2 (对应8) 和 2 1 (对应9) % 找出最后 2 个大于 5 的元素 [rows_last, cols_last] = find(A > 5, 2, 'last'); disp('最后2个:'); disp([rows_last, cols_last]); % 输出 2 1 (对应9) 和 2 3 (对应6)
重要注意事项
-
逻辑数组:
find的输入参数A可以是任何数值数组,也可以是逻辑数组(由关系运算如>, 等生成),当A是逻辑数组时,find(A)和find(A == true)的效果完全相同,并且比find(A == 1)更高效、更符合 MATLAB 的编程习惯。% 高效用法 mask = A > 5; indices = find(mask); % 不推荐,虽然也能工作 indices = find(A > 5 == 1);
-
空矩阵:
A中没有非零元素,或者没有任何元素满足条件,find将返回一个空矩阵[]。A = zeros(3, 3); index = find(A); disp(index); % 输出 []
-
多维数组: 对于多维数组(3D 矩阵),
find默认返回线性索引,如果你需要得到每一维的索引,需要指定输出参数的数量。B = cat(3, [1,0;0,2], [0,3;0,0]); % 创建一个 2x2x2 的数组 % 默认返回线性索引 lin_idx = find(B); disp(lin_idx); % 输出 1 4 6 (对应 B(1,1,1), B(2,2,1), B(1,2,2)) % 指定3个输出参数,返回第1、2、3维的索引 [r, c, d] = find(B); disp('行:'); disp(r); % 1 2 1 disp('列:'); disp(c); % 1 2 2 disp('页:'); disp(d); % 1 1 2
实际应用场景
find 命令在实际编程中非常普遍。
场景 1: 条件赋值
假设你有一个图像的灰度矩阵,想把所有亮度值大于 200 的像素点都变成白色(255)。
% 创建一个示例灰度图像矩阵 img = rand(100, 100) * 255; % 找到亮度大于 200 的像素的位置 bright_pixels = find(img > 200); % 将这些位置的像素值设置为 255 img(bright_pixels) = 255; % 或者使用更简洁的逻辑索引方式(推荐) % img(img > 200) = 255;
场景 2: 提取满足条件的元素
从一个向量中提取所有正数。
data = [-5, 10, -2, 0, 8, 15, -1]; % 找到所有正数的索引 positive_indices = find(data > 0); % 使用这些索引从原向量中提取元素 positive_values = data(positive_indices); disp(positive_values); % 输出 10 8 15
场景 3: 找到极值点的位置
假设你有一个信号,想找到它的所有峰值(即比左右邻居都大的点)。
% 创建一个示例信号
t = 0:0.1:10;
signal = sin(t) + 0.2*randn(size(t));
% 找到峰值:当前点比前一个点和后一个点都大
% 注意:要处理边界点,这里简单起见忽略
peaks_indices = find( signal(2:end-1) > signal(1:end-2) & ...
signal(2:end-1) > signal(3:end) ) + 1;
% 绘制信号并标记峰值
plot(t, signal);
hold on;
plot(t(peaks_indices), signal(peaks_indices), 'ro', 'MarkerSize', 10, 'LineWidth', 2);'Signal with Peaks Marked');
xlabel('Time'); ylabel('Amplitude');
legend('Signal', 'Peaks');
find vs. 逻辑索引
在 MATLAB 中,find 和逻辑索引(logical indexing)是实现类似功能的两种主要方式,它们各有优劣。
| 特性 | find |
逻辑索引 |
|---|---|---|
| 语法 | idx = find(A > 5); A(idx) = 10; |
A(A > 5) = 10; |
| 可读性 | 对于初学者更直观,显式地“找到”索引。 | 更简洁、更“MATLAB-like”,一行代码完成所有操作。 |
| 性能 | 对于非常大的数组,逻辑索引通常更快,因为它避免了创建中间的索引数组。 | 在底层进行了高度优化,性能通常很好。 |
| 灵活性 | 更强,可以轻松获取前N个、后N个匹配项,或者得到行列索引进行更复杂的操作。 | 灵活性稍差,主要用于直接对满足条件的元素进行操作。 |
总结与建议:
-
当你只需要对满足条件的元素进行直接操作(如赋值、提取)时,优先使用逻辑索引,它更简洁、通常更快,也更符合 MATLAB 的编程哲学。
% 推荐 A(A > 5) = 0; % 不推荐 idx = find(A > 5); A(idx) = 0;
-
当你需要知道这些元素的具体位置(索引)时,必须使用
find,当你需要记录峰值出现的时间点、或者根据索引去另一个数组中查找对应值时。% 必须使用 find peak_times = t(find(signal == max(signal)));
希望这份详细的解释能帮助你完全掌握 MATLAB 中的 find 命令!
