FORTRAN kiểu cũ yêu cầu một lập trình viên muốn tạo một phần của mảng có sẵn cho một hàm cần thiết để chuyển một tham chiếu đến toàn bộ mảng, cùng với một hoặc nhiều giá trị số nguyên chỉ định chỉ mục bắt đầu và chỉ mục kết thúc hoặc số mục . C làm cho nó có thể đơn giản hóa việc này để chuyển một con trỏ đến phần bắt đầu của phần quan tâm cùng với số phần tử. Nói một cách trực tiếp, điều này sẽ làm cho mọi thứ nhanh hơn (vượt qua hai điều chứ không phải ba). Tuy nhiên, một cách gián tiếp, nó có thể làm mọi thứ chậm lại bằng cách hạn chế các loại tối ưu hóa mà trình biên dịch có thể thực hiện.
Hãy xem xét chức năng:
void diff(float dest[], float src1[], float src2[], int n)
{
for (int i=0; i<n; i++)
dest[i] = src1[i] - src2[i];
}
nếu một trình biên dịch biết rằng mỗi con trỏ sẽ xác định bắt đầu một mảng, thì nó có thể tạo mã sẽ hoạt động theo các phần tử của mảng song song hoặc theo bất kỳ thứ tự nào, vì với bất kỳ x! = y nào, hoạt động trên mệnh [x ] sẽ không ảnh hưởng đến src1 [y] cũng như src2 [y]. Ví dụ: trên một số hệ thống, trình biên dịch có thể được hưởng lợi từ việc tạo mã tương đương với:
void dif(float dest[], float src1[], float src2[], int n)
{
int i=0;
float t1a,t1b,t2a,t2b,tsa,tsb;
if (n > 2)
{
n-=4;
t1a = src1[n+3]; t1b = src2[n+3]; t1b=src2[n+2]; t2b = src2[n+2];
do
{
tsa = t1a-t2a;
t1a = src1[n+1]; t2a = src2[n+1];
tsb = t2b-t2b;
dest[n+3] = tsa;
t1b = src1[n]; t2b = src2[n];
n-=2;
dest[n+4] = tsb;
} while(n >= 0);
... add some extra code to handle cleanup
}
else
... add some extra code to handle small values of n
}
Lưu ý rằng mọi thao tác tải hoặc tính toán một giá trị đều có ít nhất một thao tác nữa giữa nó và thao tác tiếp theo sử dụng giá trị đó. Một số bộ xử lý có thể chồng lấp quá trình xử lý các hoạt động khác nhau khi các điều kiện như vậy được đáp ứng, do đó cải thiện hiệu suất. Tuy nhiên, lưu ý rằng vì trình biên dịch C không có cách nào để biết rằng mã sẽ không được chuyển con trỏ đến các vùng chồng lấp một phần của một mảng chung, trình biên dịch C không thể thực hiện chuyển đổi ở trên. Trình biên dịch FORTRAN được cung cấp mã tương đương, tuy nhiên, có thể và đã thực hiện một chuyển đổi như vậy.
Trong khi một lập trình viên C có thể cố gắng đạt được hiệu năng tương đương bằng cách viết rõ ràng mã không kiểm soát vòng lặp và chồng chéo các hoạt động của các đường chuyền liền kề, mã đó có thể dễ dàng làm giảm hiệu suất nếu nó sử dụng quá nhiều biến tự động mà trình biên dịch phải "đổ" chúng ký ức. Trình tối ưu hóa của trình biên dịch FORTRAN có thể sẽ biết nhiều hơn một lập trình viên về các hình thức xen kẽ nào sẽ mang lại hiệu suất tối ưu trong một kịch bản nhất định và các quyết định như vậy thường được dành cho các trình biên dịch như vậy. Mặc dù C99 đã cố gắng cải thiện tình hình của C bằng cách thêm một restrict
vòng loại, nhưng chỉ có thể được sử dụng ở đây nếu dest[]
là một mảng riêng biệt từ cả hai src1[]
và src2[]
nếu lập trình viên thêm các phiên bản riêng của vòng lặp để xử lý các trường hợp trong đó tất cảdest
đã rời nhau từsrc1
và src2
, ở đâusrc1[]
và dest
bằng nhau và src2
tách rời nhau, ở đâu src2[]
và dest[]
bằng nhau và src1
tách rời nhau, và ở đó cả ba mảng đều bằng nhau. Ngược lại, FORTRAN có thể xử lý cả bốn trường hợp mà không gặp khó khăn khi sử dụng cùng một mã nguồn và cùng một mã máy.