Jump to content

Ngôn ngữ lập trình C/Khai báo/Khai báo Hàm

From Wikiversity

Hàm

[edit]

Một sự khai báo hàm là một thí dụ điển hình của một kiểu dẫn xuất. Bởi vì hàm có thể nhận vào các tham số, kiểu của mỗi tham số phải được ghi rõ ra. Tên của mỗi tham số không nhất thiết phải được cho trước khi khai báo một hàm. Hai cách khai báo sau đây là tương đương:

long bat(char);
long bat(char c);

Tham số

[edit]

Trong khi cả hai dạng trên đều đúng cú pháp, thì cách viết bỏ qua tên của các tham số thường được xét như là một dạng tồi khi viết các khai báo hàm trong các tập tin tiêu đề. Các tên này có thể cung ứng các thông tin có giá trị cho những người đọc các tập tin đó chẳng hạn như là ý nghĩa và phép toán của chúng.

Các hàm có thể nhận và trả về các kiểu con trỏ dùng cách viết thông thường cho một con trỏ:

int const *ball(long int l, int i, unsigned char *s);

Kiểu đặc biệt void hữu dụng cho việc khai báo các hàm mà chúng không có tham số nào cả:

char *wicket(void);

Điều này khác với một bộ tham số trống rỗng, được dùng trong ANSI C, để khai báo một hàm, nhưng không cho bất cứ thông tin nào về các kiểu tham số của nó.

double umpire();

Câu lệnh trên khai báo một hàm tên là umpire, nó trả về một giá trị double, nhưng không đề cập gì về các tham số mà hàm đó dùng tới.

Hàm nhận hàm khác làm tham số

[edit]

Trong C, các hàm không thể trực tiếp lấy các hàm khác như là tham số của nó, hay không thể trả về một hàm số như là kết quả. Mặc dù vậy, chúng có thể lấy vào hay trả về các con trỏ. Để khai báo rằng một hàm lấy một con trỏ hàm như là một tham số, thì dùng cách viết chuẩn như đã ghi ở trên.

int crowd(char p1, int (*p2)(void));

Khai báo bên trên có một hàm mà có hai tham số. Đối số đầu tiên, p1, là một ký tự kiểu char thông thường. Đối số còn lại, p2 là một con trỏ chỉ tới một hàm. Hàm được chỉ tới này không (nên) có các tham số, và sẽ trả về một số nguyên int.

Hàm trả về một hàm khác

[edit]

Để khai báo một hàm mà nó trả về một hàm khác phải dùng tới dấu ngoặc đơn, để thay thứ tự ưu tiên của các phép toán (về hàm)

long (*boundary(int height, int width))(int x, int y);

Như trên, có hai bộ danh sách tham số, sự khai báo này nên được đọc thật kĩ, vì nó không được rõ ràng. Ở đây, hàm boundary được định nghĩa. Nó có hai tham số nguyên heightwidth, và trả về một con trỏ hàm. Con trỏ trả về này chỉ tới một hàm mà tự hàm đó có hai tham số nguyên là xy, và trả về một số nguyên long.

Cách này có thể được mở rộng tùy ý để làm cho các hàm trả về con trỏ chỉ tới hàm mà hàm đó lại trả về các con trỏ, mà các con trỏ này chỉ tới các hàm khác, và vân vân, nhưng việc này sẽ biến mã nguồn trở nên khó hiểu một cách nhanh chóng, và rất dễ phát sinh lỗi. Nếu thấy cần thiết làm chuyện đó, thì người lập trình nên cứu xét việc thiết kế lại hay dùng một cách định nghĩa kiểu typedef.