访问者模式
需求描述:
public abstract class Packet{
abstract String getName;
}
public class ConcretePacketA extends Packet {
// Sample code
}
public class ConcretePacketB extends Packet {
// Sample code
}
public class Client {
Packet toDecode(Packet packet) {
// Sample code
}
void store(ConcretePacketA packet){
// Sample code
}
void store(ConcretePacketB packet){
// Sample code
}
// Sample code
}哪种设计模式能够解决针对toDecode返回的特定Packet类型,调用合适的store方法呢?
To address the requirement of determining the specific type of Packet and then calling the appropriate store method in your Java code, the Visitor design pattern could be a suitable solution. The Visitor pattern allows you to define a new operation without changing the classes of the elements on which it operates. It's particularly useful for operations on a set of classes with different interfaces.
Here's an overview of how you can implement the Visitor pattern in your scenario:
- Visitor Interface: Define an interface with visit methods for each type of concrete packet.
- Concrete Visitors: Implement the Visitor interface for the specific actions you want to perform on each type of packet.
- Visitable Interface in Packet Classes: Modify the
Packetclass and its subclasses to accept a visitor. - Implement the Accept Method: In each concrete
Packetsubclass, implement theacceptmethod that calls the visitor's method corresponding to its own class. - Client Code Modification: In the
Clientclass, use the Visitor to determine the type ofPacketand call the appropriatestoremethod.
Here's an example implementation based on your code:
// Visitor Interface
public interface PacketVisitor {
void visit(ConcretePacketA packetA);
void visit(ConcretePacketB packetB);
}
// Concrete Visitor
public class StorePacketVisitor implements PacketVisitor {
Client client;
public StorePacketVisitor(Client client) {
this.client = client;
}
@Override
public void visit(ConcretePacketA packetA) {
client.store(packetA);
}
@Override
public void visit(ConcretePacketB packetB) {
client.store(packetB);
}
}
// Packet classes
public abstract class Packet {
abstract void accept(PacketVisitor visitor);
}
public class ConcretePacketA extends Packet {
@Override
void accept(PacketVisitor visitor) {
visitor.visit(this);
}
// Sample code
}
public class ConcretePacketB extends Packet {
@Override
void accept(PacketVisitor visitor) {
visitor.visit(this);
}
// Sample code
}
// Client class
public class Client {
Packet toDecode(Packet packet) {
// Sample code
return packet;
}
void store(ConcretePacketA packet){
// Sample code
}
void store(ConcretePacketB packet){
// Sample code
}
void processPacket(Packet packet) {
PacketVisitor visitor = new StorePacketVisitor(this);
packet.accept(visitor);
}
// Sample code
}In this approach, when you receive a Packet from toDecode, you can use processPacket to automatically call the correct store method. The PacketVisitor will determine the type of Packet and invoke the corresponding store method on the Client instance. This pattern allows you to add new types of packets without modifying the Client class, adhering to the Open/Closed Principle.
评论已关闭