5

Tôi có một thùng chứa một loạt các con trỏ đến một lớp cơ sở và một hàm lấy một số đầu vào và trả về một lớp là lớp con của lớp cơ sở. Lớp con nào nó trả về phụ thuộc vào đầu vào.Báo cáo chuyển mạch khổng lồ cho các nhà xây dựng

Ngay bây giờ, tôi có một câu lệnh switch khổng lồ như thế này:

class Base { ... } 

class A : public Base { ... } 
class B : public Base { ... } 
... 
class Z : public Base { ... } 

Base* depends(int input) { 
    switch (input) { 
    case 1: 
     return new A(...); 
    case 2: 
     return new B(...); 
    ... 
    case 26: 
     return new Z(...); 
    default: 
     ... 
    } 
} 

tôi đã tự hỏi nếu có bất kỳ cách nào tốt hơn để thiết kế này. Tôi không biết nhiều "mẫu thiết kế" (tôi nghĩ đó là những gì họ được gọi) vì vậy tôi không biết nếu có một (rõ ràng) cách tốt hơn để thiết kế này.

+1

Thật tuyệt vời khi có từ điển ánh xạ khóa của bạn tới các lớp hoặc tên lớp (hoặc chỉ một mảng nếu khóa của bạn là int). Nhưng điều này có thể? Xem câu hỏi tương tự: http://stackoverflow.com/questions/582331/c-is-there-a-way-to-instantiate-objects-from-a-string-holding-their-class-name –

+0

@Ray cảm ơn đối với liên kết, câu hỏi đó rất giống với câu hỏi của tôi, và câu trả lời khá nhiều cho câu hỏi. –

Trả lời

6

Điều bạn đang tìm kiếm là Factory Method pattern.

Điều quan trọng ở đây là loại bỏ sự cần thiết cho lớp cơ sở để có bất kỳ kiến ​​thức nào về triển khai lớp dẫn xuất. Đó là một thiết kế tồi cho một lớp cơ sở để có kiến ​​thức về các lớp có nguồn gốc.

Mẫu phương thức của nhà máy giải quyết vấn đề trên khi quá trình tạo diễn ra bên ngoài lớp Cơ sở.

1

Hơi khó để tìm ra những gì bạn đang có ý định, nhưng bạn có thể muốn xem xét một mẫu Abstract Factory nếu bạn muốn tạo một loạt các lớp con khác nhau dựa trên một số tham số đầu vào.

1

cách khác là tạo một mảng nơi bạn sẽ đặt con trỏ đến các hàm sẽ gọi hàm tạo tương ứng. Và trong phụ thuộc của bạn() bạn chỉ sẽ gọi hàm mà bạn cần bằng cách đưa vào. Nhưng bất kỳ cách nào bạn cần 26 chức năng trong phương pháp này

1

Tham số nguyên "đầu vào" xuất phát từ đâu đó. Bạn có thể cho phép mã tạo ra rằng int tạo đối tượng thực tế thay thế. Điều đó sẽ không hoạt động nếu bạn đang đọc int từ đĩa hoặc một cái gì đó như thế.

Bạn có thể xem xét việc thiết lập tình huống trong đó các lớp con khác nhau tự đăng ký với đối tượng tạo ra chúng. Trong trường hợp đó, đối tượng nhà máy sẽ không cần biết về các lớp con tại thời gian biên dịch. Bạn có thể thực hiện việc này tại thời điểm khởi động bằng cách sử dụng các biến toàn cục mà các nhà thầu của chúng ta thực hiện đăng ký cho mỗi lớp con. Câu lệnh switch của bạn đơn giản và nhanh hơn, nhưng nó có nghĩa là bạn phải giữ cho switch được cập nhật khi bạn thay đổi các lớp con. Đó là một thương mại và tôi không nghĩ rằng giải pháp của bạn nhất thiết phải thua kém một giải pháp phức tạp hơn.

+0

Thật không may đó là chính xác những gì chương trình này không - đọc dữ liệu từ một tập tin. Chương trình này cần mỗi chút hiệu quả nó có thể nhận được mặc dù, vì vậy tôi nghĩ rằng gắn bó với một 'switch' sẽ là một cách tốt để đi. Cảm ơn. –

+0

@Seth Carnegie Một điều bạn có thể muốn làm là có các lớp con định nghĩa một trường const tĩnh như classId. Sau đó cả hai mã tạo đối tượng và mã ghi ra id vào đĩa đều có thể tham chiếu đến cùng một trường. –

+0

vâng, đó là những gì nó làm. Tôi thà làm điều đó mà RTTI. –