2012-04-03 30 views
7

tôi có mã này:chức năng ảo trọng và ẩn

class Event{}; 
class CustomEvent:public Event{}; 

class Handler 
{ 
    public: 
     virtual void inform(Event e){} 
}; 

class CustomHandler : public Handler 
{ 
    public: 
    void inform(CustomEvent e){}   

}; 

CustomEvent cEvent; 
Handler* handler = new CustomHandler; 

//this calls Handler::inform(Event), not CustomHandler::(CustomEvent) , as I expected 
handler->inform(cEvent); 

Nếu tôi thay đổi mã này:

class Handler 
{ 
    public: 
     virtual void inform(Event e){} 
     virtual void inform(CustomEvent e){} 

}; 

class CustomHandler : public Handler 
{ 
    public: 
    void inform(CustomEvent e){}   

}; 

CustomEvent cEvent; 
Handler* handler = new CustomHandler; 

//this calls CustomHandler::(CustomEvent) 
handler->inform(cEvent); 

Tôi đọc mà này được kết nối với chức năng trọng và ẩn nhưng vẫn doesn' t hiểu hành vi trong mã này.

+3

Rất nhiều điều sai với mã. Đối với người mới bắt đầu, các đối số hàm sẽ là * references *. –

+0

Tại sao phải tham khảo? – user152508

+2

Vì (a) cắt và (b) một bản sao không cần thiết. – ipc

Trả lời

9

Tái định nghĩa hàm không làm việc dựa trên runtime loại các đối số (mà cho lập luận của bạn ở đây là CustomHandler*) nhưng thay vào họ tĩnh loại (mà ở đây là Handler*, như đó là những gì handler được khai báo là) .

Chức năng ảo cho phép bạn thực hiện các cuộc gọi chức năng dựa trên loại thời gian chạy là một đối tượng (đối tượng bạn gọi hàm). Gửi các cuộc gọi dựa trên kiểu thời gian chạy của nhiều đối tượng được gọi là nhiều công văn; trong instace này, chúng ta đang nói về trường hợp phổ biến nhất của double dispatch. Nếu bạn muốn loại chức năng này, bạn sẽ phải thực hiện công văn kép hoặc sử dụng một thư viện mà nó cho bạn.

Visitor pattern là cách khá phổ biến để thực hiện việc triển khai; xem thêm Difference betwen Visitor pattern & Double Dispatch.

Cuối cùng, bạn có thể tìm thấy một cuộc thảo luận hay về Khách truy cập bao gồm mã mẫu (cuộn xuống) here.

+0

+1 bạn đã viết những gì tôi định trả lời. ngoại trừ tôi dự định bao gồm một ví dụ mẫu khách truy cập cụ thể. xin vui lòng thêm rằng –

+0

@ Cheersandhth.-Alf: Thêm một liên kết mà nên làm tốt. Tôi không muốn thêm một ví dụ nội tuyến (quá nhiều boilerplate). – Jon

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