Java 如何将实例成员耦合到实例方法?
我的班级结构如下:Java 如何将实例成员耦合到实例方法?,java,design-patterns,Java,Design Patterns,我的班级结构如下: public interface DBReader { public Map<String, String> read(String primaryKey, String valueOfPrimaryKey, boolean scanIndexForward, boolean consistentRead, int maxPageSize); public int getA(String ___); public int ge
public interface DBReader {
public Map<String, String> read(String primaryKey, String valueOfPrimaryKey,
boolean scanIndexForward, boolean consistentRead, int maxPageSize);
public int getA(String ___);
public int getB(String ___);
public int getC(String ___);
}
公共接口DBReader{
公共映射读取(字符串primaryKey、字符串值primaryKey、,
boolean scanIndexForward、boolean consistentRead、int maxPageSize);
公共int getA(字符串_;);
公共int getB(字符串_;);
公共int getC(字符串_;);
}
公共类DynamoDBReader实现DBReader{
私人发电机;
私有字符串表名;
私人餐桌;
专用int吞吐量;
私人发电机(建筑商){
this.through=builder.through;
this.tableName=builder.tableName;
this.dynamoDB=builder.dynamoDB;
this.table=dynamoDB.getTable(builder.tableName);
如果(表==null){
抛出新的InvalidParameterException(String.format(“表%s不存在。”,tableName));
}
}
@凌驾
公共整数getA(字符串___;){
读取(uuuuuuuuuuuuuuuuuuuu);
}
返回;
}
@凌驾
公共int getB(字符串___;){
读取(uuuuuuuuuuuuuuuuuuuu);
}
返回;
}
@凌驾
公共整数getC(字符串_____;){
读取(uuuuuuuuuuuuuuuuuuuu);
}
返回;
}
@凌驾
公共映射读取(字符串primaryKey、字符串primaryKey值、布尔扫描索引forward、,
boolean consistentRead,int maxPageSize){
QuerySpec spec=新QuerySpec()
.withHashKey(primaryKey、valueOfPrimaryKey)
.向前带有扫描索引(向前扫描索引)
.使用consistentRead(consistentRead)
.withMaxPageSize(maxPageSize);
ItemCollection items=table.query(spec);
迭代器Iterator=items.firstPage().Iterator();
Map itemValues=新的HashMap();
while(itemIterator.hasNext()){
Item=itemIterator.next();
}
返回项目值;
}
}
@可视性测试
受保护的无效设置(表格){
this.table=表格;
}
/**
*返回一个新的生成器。
*/
公共静态生成器(){
返回新的生成器();
}
公共静态类生成器{
私有字符串表名;
专用int吞吐量;
私人发电机;
私有生成器(){}
公共生成器tableName(字符串tableName){
this.tableName=tableName;
归还这个;
}
公共建筑商吞吐量(整数吞吐量){
这个。吞吐量=吞吐量;
归还这个;
}
公共建筑商dynamoDB(dynamoDB dynamoDB){
this.dynamoDB=dynamoDB;
归还这个;
}
公共DynamoDBReader构建(){
if(tableName==null){
抛出新的InvalidParameterException(“表名不能为null”);
}
if(吞吐量)
在我看来,为不同的getter创建子类的解决方案不是一个好主意
你能解释一下原因吗
我一直听说,‘我不喜欢……’、‘这看起来很难看……’、‘不应该这样做’。不喜欢某个特定解决方案的原因应该有客观原因支持,而不是个人观点。大多数时候,我们作为开发人员的直觉告诉我们,当某个问题实际上违反了某些软件开发原则时,它是错误的。但有时,这只是单纯的个人感觉,没有任何特定的逻辑原因。当这种情况发生时,我喜欢谈论细节
您的解决方案违反了一个基本的软件原则,称为
拥有将是更好的解决方案。为什么DynamoDBReader.getA()
没有实现DBReader.getA()
?我已经更新了代码片段(它不是实际的代码:泄露的秘密)。我认为,我的问题实际上与代码片段的正确性是正交的。与创建所有内容都与提供的类一起工作且不需要额外解释的类相比,使用只有在特定条件下才有意义的getter是一个糟糕得多的主意。这不是一个可靠的设计。无效的方法调用会引发NoSuchMethodExcep选项。每个表都需要一个派生类,每个表都需要相应列的getter和setter。或者,一个Map。我必须为每个表创建一个子类,每个表实际上只能通过单个方法访问。实际上,有一些设计模式和众所周知的接口是基于单个方法的思想构建的。Command模式及其在Java中的可运行表示就是很好的例子。单一方法类不被认为是缺点,它也不一定是违反SRP的好理由。实际上,这正是SRP的全部内容。
public class DynamoDBReader implements DBReader {
private DynamoDB dynamoDB;
private String tableName;
private Table table;
private int throughput;
private DynamoDBReader(Builder builder) {
this.throughput = builder.throughput;
this.tableName = builder.tableName;
this.dynamoDB = builder.dynamoDB;
this.table = dynamoDB.getTable(builder.tableName);
if (table == null) {
throw new InvalidParameterException(String.format("Table %s doesn't exist.", tableName));
}
}
@Override
public int getA(String ____) {
read(_________);
}
return ________;
}
@Override
public int getB(String ____) {
read(_________);
}
return ________;
}
@Override
public int getC(String ____) {
read(_________);
}
return ________;
}
@Override
public Map<String, String> read(String primaryKey, String valueOfPrimaryKey, boolean scanIndexForward,
boolean consistentRead, int maxPageSize) {
QuerySpec spec = new QuerySpec()
.withHashKey(primaryKey, valueOfPrimaryKey)
.withScanIndexForward(scanIndexForward)
.withConsistentRead(consistentRead)
.withMaxPageSize(maxPageSize);
ItemCollection<QueryOutcome> items = table.query(spec);
Iterator<Item> itemIterator = items.firstPage().iterator();
Map<String, String> itemValues = new HashMap<String, String>();
while (itemIterator.hasNext()) {
Item item = itemIterator.next();
}
return itemValues;
}
}
@VisibleForTesting
protected void setTable(Table table) {
this.table = table;
}
/**
* Returns a new builder.
*/
public static Builder builder() {
return new Builder();
}
public static class Builder {
private String tableName;
private int throughput;
private DynamoDB dynamoDB;
private Builder() { }
public Builder tableName(String tableName) {
this.tableName = tableName;
return this;
}
public Builder throughput(int throughput) {
this.throughput = throughput;
return this;
}
public Builder dynamoDB(DynamoDB dynamoDB) {
this.dynamoDB = dynamoDB;
return this;
}
public DynamoDBReader build() {
if (tableName == null) {
throw new InvalidParameterException("Table name can't be null.");
}
if (throughput <= 0) {
throw new InvalidParameterException("Throughput should be > 0.");
}
if (dynamoDB == null) {
throw new InvalidParameterException("dynamoDB can't be null.");
}
return new DynamoDBReader(this);
}
}
}