2008-10-31 32 views
30

Tôi đã tự dạy mình Mục tiêu-C trong tháng qua hoặc hơn (tôi là một người đứng đầu Java) và tôi đã có bộ não của tôi bao quanh hầu hết trong số đó ngay bây giờ. Một điều khiến tôi bối rối vào lúc này: Sự khác biệt giữa việc nhập một lớp học qua @class vs làm một #import là gì?Sự khác biệt giữa #import và @class là gì và khi nào tôi nên sử dụng cái kia?

Có tốt hơn một loại khác không, hoặc tôi có cần sử dụng cái này thay cho cái khác trong một số trường hợp nhất định không? Tôi đã sử dụng chỉ #import cho đến nay.

Trả lời

66

#import đưa toàn bộ tệp tiêu đề được đề cập vào tệp hiện tại; bất kỳ tệp nào THAT tệp #import cũng được bao gồm. @class, mặt khác (khi được sử dụng trên một dòng của chính nó với một số tên lớp), chỉ cần nói với trình biên dịch "Này, bạn sẽ thấy một mã thông báo mới sớm; nó là một lớp, vì vậy đối xử với nó theo cách đó).

Điều này rất hữu ích khi bạn có tiềm năng cho 'bao gồm vòng tròn', tức là, Object1.h làm cho tham chiếu đến Object2 và Object2.h làm cho tham chiếu đến Object1.Nếu bạn #import cả hai tệp vào khác, trình biên dịch có thể bị lẫn lộn vì nó cố gắng để #import Object1.h, nhìn vào nó và thấy Object2.h; nó cố gắng để #import Object2.h, và nhìn thấy Object1.h, vv

Nếu, mặt khác, mỗi trong số các tệp đó có @class Object1; hoặc @class Object2;, thì không có tham chiếu vòng tròn nào. t chắc chắn thực sự là #import các tiêu đề bắt buộc vào tệp triển khai (.m) của bạn.

+2

Ben, Ben, bạn không cần phải trả lời mọi câu hỏi Cocoa trên Stack Overflow. Bạn sẽ đốt cháy! – schwa

+2

phải ... dừng ... trả lời ... –

5

Điều khác bạn muốn ghi nhớ là #imports làm chậm thời gian biên dịch của bạn, vì nó có nghĩa là trình biên dịch cần kéo và làm việc thông qua nhiều tệp tiêu đề khác. Điều này chủ yếu được che giấu bởi việc sử dụng các tiêu đề biên dịch sẵn, nhưng đôi khi tôi đã được trao các dự án mà corss nhập khẩu mỗi tiêu đề thay vì sử dụng @class khi thích hợp, và sửa chúng có thể cải thiện thời gian biên dịch. Đó là cách tinh tế hệ thống củng cố thực tế là nếu bạn chỉ sử dụng những gì bạn thực sự cần mọi thứ đi nhanh hơn.

Như một quy tắc chung, tôi luôn sử dụng khai báo @class trong các tệp tiêu đề của tôi và chỉ #import siêu lớp. Điều đó phù hợp với những gợi ý của Ben, nhưng tôi nghĩ rằng đáng chú ý là ngay cả khi bạn không lo lắng về refs tròn, bạn nên hạn chế #imports trong các tệp tiêu đề nếu có thể.

27

@class được gọi là khai báo chuyển tiếp . Về cơ bản, bạn đang nói cho trình biên dịch biết rằng lớp tồn tại nhưng không phải bất cứ điều gì về lớp. Vì vậy, nó không biết những thứ như siêu lớp của nó và những phương thức mà nó tuyên bố.

Theo nguyên tắc chung, hãy sử dụng @class trong .h và #import trong .m, nếu có thể. Như Louis đã nói, nó sẽ giúp tăng tốc thời gian biên dịch. Tuy nhiên, đôi khi bạn cần phải có #import một lớp trong tiêu đề. Trường hợp tôi có thể nghĩ ngay bây giờ là:

  • Bạn đang subclassing một lớp
  • Bạn đang thực hiện một giao thức

Trong những trường hợp này, bạn phải #import file header nơi lớp hoặc giao thức là tuyên bố vì trình biên dịch cần phải biết phân cấp đầy đủ của các lớp cha và các giao thức thực hiện của nó.

FWIW, bạn có thể chuyển tiếp tuyên bố các giao thức cũng vậy, miễn là bạn không thực hiện chúng:

@protocol SomeProtocol; 

@interface ... 

- (id<SomeProtocol>)someMethod; 

@end 
Các vấn đề liên quan