2009-10-16 32 views
9

Có điều gì sai khi có một lớp đơn (một .h) được triển khai trên nhiều tệp nguồn không? Tôi nhận ra rằng điều này có thể là một triệu chứng của quá nhiều mã trong một lớp duy nhất, nhưng có bất cứ điều gì về mặt kỹ thuật sai với nó?Một lớp học có nhiều tệp triển khai

Ví dụ:

foo.h

class Foo 
{ 
    void Read(); 
    void Write(); 
    void Run(); 
} 

Foo.Read.cpp

#include "Foo.h" 
void Foo::Read() 
{ 
} 

Foo.Write.cpp

#include "Foo.h" 
void Foo::Write() 
{ 
} 

Foo.Run.cpp

#include "Foo.h" 
void Foo::Run() 
{ 
} 

Trả lời

13

Điều này là tốt. Cuối cùng, nó sẽ được liên kết với nhau.

Tôi thậm chí đã thấy mã, trong đó mọi chức năng của thành viên nằm trong một tệp * .cpp khác.

+1

Điều đó sẽ khiến tôi bất hợp pháp. Tôi chắc chắn có đôi khi tốt (hoặc ít nhất là phong nha) lý do để làm điều này, nhưng từ quan điểm của cố gắng để hiểu mô hình đối tượng, bleah ... để có để nhảy các tập tin để làm theo các phương pháp xung quanh. – Joe

+1

Nếu bạn xây dựng một thư viện, việc tách mọi chức năng và toàn cầu thành đối tượng riêng của nó cho phép người tiêu dùng chỉ liên kết các bit mà họ tham chiếu và không còn nữa. Mặc dù vậy, thật khó chịu khi làm việc. – ephemient

+1

@ephemient: Tại sao điều này lại quan trọng? Không thể một trình liên kết loại bỏ các chức năng mà bạn không sử dụng? Hoặc là nó chỉ để cải thiện thời gian liên kết? –

4

Không, không có gì sai về mặt kỹ thuật với nó. Trình liên kết sẽ đưa tất cả các phần của Foo vào trong nhị phân cuối cùng.

1

Tôi đã làm việc với Thời gian chạy di động Apache, điều này thực hiện khá nhiều điều chính xác này. Bạn có một tiêu đề, giả sử apr_client.h và nhiều tệp triển khai cho các hàm trong tiêu đề đó - mỗi tệp đại diện cho một khía cạnh của các hoạt động của máy khách. Nó không sai, và nó không thực sự khác thường.

này có thể là một triệu chứng của quá nhiều mã trong một lớp duy nhất

C++ không phải là Java, vì vậy bạn không cần phải chọn tên tập tin của bạn theo tên lớp học của bạn.

0

yea thats legitmate, và trên thực tế các ngôn ngữ mới hơn như C# thực hiện loại điều đó mọi lúc.

6

Đó là hợp pháp và nó có một số lợi thế (!?) ...

Nếu bạn liên kết thực thi của bạn với thư viện tĩnh của lớp này, chỉ có các chức năng sử dụng sẽ nhận được. Điều này là rất tiện dụng cho hạn chế hệ thống nguồn.

Bạn cũng có thể ẩn chi tiết triển khai của một số chức năng nhất định. Hai người có thể thực hiện các phần của một lớp mà không biết về nhau. Tiện dụng cho các dự án DOD.

Nếu bạn xem bất kỳ nguồn CRT nào, bạn sẽ thấy cùng một mẫu ...

+1

Chi tiết triển khai lại các điểm ẩn cho cùng một lớp thực sự là kéo dài nó. Nếu bạn có một lớp học có thể được phân chia dễ dàng như vậy, sau đó nó phải là 2 lớp học không phải một. –

+0

@Richard: Vâng, tôi chỉ muốn nói rằng bạn có thể làm điều đó, bạn không phải làm điều đó. Nếu hàm rất đơn giản, thì bạn có thể không muốn tạo một lớp riêng cho nó ... – Malkocoglu

+1

@Richard - eh? - những gì về một "thiết bị" ví dụ foo :: đọc foo :: viết foo :: ioctl những gì về những lợi ích của thời gian xây dựng ngắn hơn? – pgast

2

Nó hoàn toàn hợp lệ. Tất cả các tệp cpp sẽ được liên kết với nhau. Điều này có thể hữu ích, như bạn đã nói, làm cho một tệp triển khai rất lớn dễ đọc hơn và vì mỗi tệp cpp là một đơn vị biên dịch, bạn có thể (ab) sử dụng thực tế đó. (Các không gian tên chưa đặt tên chẳng hạn)

+0

+ để đề cập đến cơ hội tăng thêm cho liên kết nội bộ –

0

Có hai điểm đáng xem xét.

Lớp optimisations rộng:

Nếu trình biên dịch có tất cả các chức năng thành viên có thể nhìn thấy nó khi nó phân tích các tập tin (giả sử một trình biên dịch TU duy nhất) sau đó nó có thể thực hiện optimisations giữa các thành viên khác chức năng.

Mã xét

Nếu tất cả các định nghĩa cho một lớp là trong cùng TU, sau đó điều này làm thủ công đang rà soát dễ dàng hơn. Nếu các định nghĩa được chia thành các TU khác nhau, điều này làm tăng đáng kể nỗ lực cần thiết để xem xét thủ công khi các tệp thích hợp cần phải được tìm kiếm, với việc nhấp nháy liên tục giữa các cửa sổ để có được hình ảnh "toàn bộ".

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