如何避免忘记处理属性?

时间:2011-06-10 15:05:29

标签: java oop

有这个课程

Class Test
{ 
  static int version=1;
  String A;
  String B;

  //constructor
  //setters, getters, etc...      
  public void printAll(void)
  {
     System.out.println(A);
     System.out.println(B);
  }    
}

过了一会儿,我们修改了Class来添加一个String C:

Class Test
{ 
  static int version=2;
  String A;
  String B;
  String C;

  //constructor
  //setters, getters, etc...      
  public void printAll(void)
  {
     System.out.println(A);
     System.out.println(B);
     //it seems somebody has forgotten to print C!!!!!!!!!

  }    
}

这里有一些已知的方法来避免这种错误吗?

由于

7 个答案:

答案 0 :(得分:3)

代码审查应该抓住这个问题。除了代码审查之外,单元测试或调试通常会告诉您代码是否表现如何。如果您没有处理某些属性,则测试应该失败,因为在某些时候方法/属性/结果将不正确。除了那些我认为使用反射的东西是过分的。

答案 1 :(得分:1)

我不确定是否推荐,但您可以通过以下方式获取对象的字段:

import java.lang.reflect.Field;

Field[] fields = object.getClass().getDeclaredFields();
for (int i = 0 ; i < fields.length ; i++)
  System.out.println(fields[i]);

答案 2 :(得分:1)

您有一些代码在某个地方添加,删除或修改,会影响其他代码。在这种特殊情况下,您的函数会调用所有属性。

您可能想要像C ++这样的东西,其中类没有像Java这样的显式属性,并且使用宏或集合进行模拟。


package mycompany.myapp;

import propertiesgenerics;

Class Test
{ 
  static int version=1;

  public property<String> A;
  public property<String> B;
  public list< property<string> > Properties;

  public Bicycle() {
    public property<String> A = new property<String>();
    public property<String> B = new property<String>();

    Properties.add(A);
    Properties.add(B);
  }


  //constructor
  //setters, getters, etc...      
  public void printAll(void)
  {
    // iterating thru this.properties
    for loop {
     System.out.println(eachProperty);
     } // for loop
  }    
}

如果不是滥用反射的粉丝,由于并非所有字段都被视为属性,并且并非所有属性都被视为字段。

答案 3 :(得分:1)

您可以使用org.apache.commons.lang.builder.ToStringBuilder

public void printAll() {
        System.out.println(ToStringBuilder.reflectionToString(this));
}

public void printAll() {
    System.out.println(new ToStringBuilder(this).
       append("name", name).
       append("age", age).
       append("smoker", smoker).
       toString());
}

答案 4 :(得分:1)

您可以使用注释来使用更加结构化的方式来使用反射,您可以更好地控制哪些字段可以打印:

@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.FIELD})
@interface Printable { }

class Test {

  @Printable String A;
  @Printable String B;
  @Printable String C;

  public void printAll() {
    for (Field field : getClass().getDeclaredFields()) {
      if (field.isAnnotationPresent(Printable.class)) {
        try {
          System.out.println(field.get(this));
        } catch (Exception e) {
          throw new RuntimeException(e);
        }       
      }
    }
  }

}

答案 5 :(得分:0)

有时,最好的策略就是将评论放在您的资产列表之上:

// Remember to include any new properties in the printAll method!
String A;
String B;

除此之外,我同意KyleM的观点,即代码审查对于解决此类问题至关重要。

答案 6 :(得分:-2)

我不确定我是否会将健忘视为一个错误。我认为处理这类事情的最佳方法是使用源代码控制程序,以便跟踪对文件的更改。

http://tortoisesvn.net/:这是一个很好的