Lập trình · Ngôn ngữ lập trình
Hướng dẫn MATLAB cho người mới bắt đầu
Trả lời nhanh
MATLAB là ngôn ngữ và môi trường tính toán số của MathWorks, trong đó mọi giá trị đều là ma trận. Bạn viết A * B cho tích ma trận, A .* B cho phép nhân từng phần tử, đánh chỉ số từ 1, và thay nhiều vòng lặp bằng biểu thức vector hóa. MATLAB có sẵn tính năng vẽ đồ thị và một bộ toolbox lớn cho kỹ thuật và khoa học. GNU Octave là lựa chọn thay thế miễn phí, mã nguồn mở, chạy được hầu hết mã MATLAB cơ bản mà không cần sửa.
MATLAB là gì và ai dùng nó
MATLAB ("matrix laboratory") khởi đầu là công cụ của Cleve Moler để dễ dàng truy cập các thư viện đại số tuyến tính và trở thành sản phẩm thương mại của MathWorks. Nó kết hợp một ngôn ngữ, môi trường làm việc tương tác, vẽ đồ thị và các toolbox cho xử lý tín hiệu, hệ thống điều khiển, tối ưu hóa, thống kê, xử lý ảnh và học máy. Simulink, sản phẩm đi kèm, mô hình hóa hệ động lực bằng sơ đồ khối.
MATLAB được dùng rộng rãi trong các khóa học kỹ thuật và khoa học, phòng thí nghiệm nghiên cứu và các ngành như ô tô, hàng không vũ trụ và tài chính. Nó cần giấy phép trả phí (nhiều trường đại học cung cấp sẵn). GNU Octave là phần mềm tự do với cú pháp phần lớn tương thích; nó bao quát ngôn ngữ cốt lõi và nhiều hàm, nhưng không có toolbox của MathWorks hay Simulink.
Cài đặt và chạy Hello, world
Cài MATLAB từ MathWorks, dùng MATLAB Online trong trình duyệt, hoặc cài GNU Octave từ octave.org (Windows, macOS, Linux). Mã được lưu trong tệp .m. Script là một tệp chứa các lệnh; bạn chạy nó bằng cách gõ tên tệp, không kèm .m, trong Command Window.
% hello.m
disp('Hello, world!')matlab -batch "hello" # MATLAB from a terminal
octave hello.m # GNU Octave
# Hello, world!Chú thích bắt đầu bằng %. Dòng không kết thúc bằng dấu chấm phẩy sẽ in kết quả, nên x = 5 hiển thị x = 5, còn x = 5; thì im lặng.
Biến và các kiểu cơ bản
Biến được tạo bằng phép gán và không cần khai báo. Số mặc định là double (dấu phẩy động 64 bit), và ngay cả một số đơn lẻ cũng là ma trận 1x1.
| Kiểu | Ví dụ | Ghi chú |
|---|---|---|
| double | x = 3.14 | Kiểu số mặc định |
| Kiểu số nguyên | n = int32(42) | int8 đến int64, uint8 đến uint64; phép tính bị chặn ở giá trị biên (saturate) |
| logical | ok = true | Kết quả của phép so sánh như x > 2 |
| char array | name = 'Ana' | Dấu nháy đơn; một vector hàng gồm các ký tự |
| string | s = "Ana" | Đối tượng chuỗi của MATLAB; Octave coi dấu nháy kép là mảng char |
| cell array | c = {'Ana', 30} | Chứa các giá trị thuộc nhiều kiểu khác nhau |
| struct | p.name = 'Ana' | Các trường có tên |
x = 10;
y = 3;
x / y % 3.3333
mod(x, y) % 1
x ^ 2 % 100
name = 'Ana';
fprintf('%s is %d years old\n', name, 30)
% Ana is 30 years old
class(x) % 'double'Vector và ma trận
Dấu ngoặc vuông tạo mảng: dấu cách hoặc dấu phẩy ngăn cách các cột, dấu chấm phẩy ngăn cách các hàng. Lập chỉ số dùng dấu ngoặc đơn và bắt đầu từ 1; end nghĩa là chỉ số cuối và : nghĩa là "tất cả".
v = [3 1 4 1 5];
v(1) % 3
v(end) % 5
v(2:4) % [1 4 1]
v * 2 % [6 2 8 2 10]
v(v > 2) % [3 4 5] logical indexing
A = [1 2; 3 4];
A(2, :) % second row: [3 4]
A' % transpose: [1 3; 2 4]
A * A % matrix product: [7 10; 15 22]
A .* A % element-wise: [1 4; 9 16]
b = [5; 11];
x = A \ b % solves A*x = b: [1; 2]
z = zeros(2, 3); % also ones, eye, rand
r = 0:0.25:1; % [0 0.25 0.5 0.75 1]Toán tử có dấu chấm (.*, ./, .^) chạy theo từng phần tử; không có dấu chấm thì theo quy tắc đại số tuyến tính. Toán tử gạch chéo ngược giải hệ tuyến tính và chính xác hơn việc tính inv(A) * b.
Luồng điều khiển
score = 85;
if score >= 90
disp('A')
elseif score >= 80
disp('B')
else
disp('C')
end
total = 0;
for k = 1:10
total = total + k;
end
fprintf('total = %d\n', total) % total = 55
n = 3;
while n > 0
n = n - 1;
end
switch 'red'
case {'red', 'green'}
disp('a color')
otherwise
disp('unknown')
endMọi khối đều kết thúc bằng end. Nhiều vòng lặp có thể thay bằng biểu thức vector hóa: vòng lặp ở trên tương đương sum(1:10), ngắn hơn và thường nhanh hơn. Nếu buộc phải xây mảng trong vòng lặp, hãy cấp phát trước, ví dụ result = zeros(1, 1000);.
Hàm và hàm ẩn danh
Một hàm nằm trong tệp riêng có tên trùng với tên hàm. Một hàm có thể trả về nhiều giá trị. Trong các phiên bản MATLAB gần đây, script cũng có thể chứa các hàm cục bộ ở cuối tệp.
% stats.m
function [m, s] = stats(x)
%STATS Mean and sample standard deviation of a vector.
m = mean(x);
s = std(x);
end[m, s] = stats([2 4 4 5 7]) % m = 4.4000, s = 1.8166
[biggest, where] = max([3 9 2]) % biggest = 9, where = 2
f = @(x) x.^2 + 1; % anonymous function
f(3) % 10
f([1 2 3]) % [2 5 10]
fzero(@(x) x.^2 - 2, 1) % 1.4142, a root near 1
integral(f, 0, 1) % 1.3333Hàm ẩn danh, tạo bằng @, thường được truyền cho các hàm khác như fzero, integral, arrayfun hoặc các thủ tục tối ưu hóa. Hãy viết chúng bằng toán tử theo từng phần tử (.^) để chúng cũng chạy được trên vector.
Struct và cell array
person.name = 'Ana';
person.age = 30;
fprintf('%s is %d\n', person.name, person.age) % Ana is 30
c = {'Ana', 30, [1 2 3]}; % cell array with mixed types
c{2} % 30 (curly braces get the content)
class(c(2)) % 'cell' (parentheses get a sub-cell)
names = {'Ana', 'Ben', 'Cleo'};
numel(names) % 3
upper(names{1}) % 'ANA'MATLAB còn có kiểu table cho dữ liệu theo cột với các biến có tên, giống bảng tính; readtable nạp tệp CSV và Excel vào đó.
Xử lý lỗi
Phát sinh lỗi bằng error, có thể kèm mã định danh như 'demo:negative', và xử lý bằng try ... catch. Đối tượng bắt được (MException trong MATLAB) có các trường identifier và message.
% safe_sqrt.m
function r = safe_sqrt(x)
if x < 0
error('demo:negative', 'Input must be non-negative, got %g', x);
end
r = sqrt(x);
endtry
safe_sqrt(-4);
catch err
fprintf('%s: %s\n', err.identifier, err.message)
end
% demo:negative: Input must be non-negative, got -4Dùng warning(...) cho các vấn đề không nên dừng chương trình. Nếu không có bước kiểm tra, sqrt(-4) sẽ không lỗi: nó trả về số phức 0 + 2i.
Một chương trình hoàn chỉnh nhỏ: phân tích và vẽ dữ liệu
% temps.m - analyze a week of temperatures
temps = [21.5 23.0 19.8 25.1 24.3 18.9 22.7];
days = 1:numel(temps);
avg = mean(temps);
[hottest, idx] = max(temps);
above = days(temps > avg);
fprintf('Average: %.2f\n', avg)
fprintf('Hottest: %.1f on day %d\n', hottest, idx)
fprintf('Days above average: %s\n', mat2str(above))
plot(days, temps, '-o')
hold on
plot(days, avg * ones(size(days)), '--')
xlabel('Day'); ylabel('Temperature (C)')
title('Temperatures this week')
legend('Daily', 'Average')
% Average: 22.19
% Hottest: 25.1 on day 4
% Days above average: [2 4 5 7]Script dùng chỉ số logic để tìm những ngày cao hơn mức trung bình mà không cần vòng lặp, rồi vẽ biểu đồ đường có dấu điểm và một đường trung bình nét đứt. Cùng đoạn mã này chạy được trong GNU Octave.
Học tiếp ở đâu
- Tài liệu MATLAB của MathWorks, bắt đầu từ các trang bắt đầu nhanh.
- MATLAB Onramp, khóa học nhập môn tương tác miễn phí của MathWorks.
- Sách hướng dẫn GNU Octave nếu bạn dùng Octave, gồm các ghi chú về khả năng tương thích với MATLAB.
- Tiếp theo hãy học vector hóa,
readtablecho tệp dữ liệu và các hàm vẽ đồ thị.
Câu hỏi thường gặp
Có phiên bản MATLAB miễn phí không?
Bản thân MATLAB cần giấy phép, dù MathWorks có bản dùng thử và nhiều trường đại học cung cấp giấy phép toàn trường. GNU Octave là chương trình mã nguồn mở miễn phí, chạy được hầu hết mã MATLAB cơ bản.
Khác nhau giữa * và .* trong MATLAB là gì?
* là phép nhân ma trận trong đại số tuyến tính, đòi hỏi các chiều trong khớp nhau. .* nhân các phần tử tương ứng của hai mảng cùng kích thước.
GNU Octave có hoàn toàn tương thích với MATLAB không?
Không hoàn toàn. Cú pháp cốt lõi, ma trận, hàm và vẽ đồ thị phần lớn tương thích, nhưng Octave không có toolbox của MathWorks, Simulink và một số tính năng MATLAB mới hơn, và nó chấp nhận thêm vài dạng cú pháp riêng.
Vì sao MATLAB đánh chỉ số từ 1?
MATLAB theo ký hiệu toán học, trong đó phần tử đầu tiên của vector hoặc ma trận là phần tử 1. Fortran, R và Julia dùng cùng quy ước này.
Nên học MATLAB hay Python?
Hãy học MATLAB nếu khóa học, phòng thí nghiệm hoặc công ty của bạn dùng nó, đặc biệt với Simulink hoặc các toolbox cụ thể. Python với NumPy, SciPy và Matplotlib miễn phí và đa dụng hơn, và các khái niệm dùng chung được giữa hai bên.