- iOS/Objective-C 元类和类别
- objective-c - -1001 错误,当 NSURLSession 通过 httpproxy 和/etc/hosts
- java - 使用网络类获取 url 地址
- ios - 推送通知中不播放声音
我的一位前同事半小时前开始讨论 JavaBeans,以及为什么它们在 JSF 中不能按照他想要的方式工作。特殊情况是关于 boolean 属性。
1。对于名为 isUrl
的 boolean 属性,Eclipse 生成此
private boolean isUrl;
public boolean isUrl() {..}
public boolean setUrl(boolean url) {..}
但这在 JSF 中不起作用。他通过添加 public boolean getIsUrl()
使其工作。实现可能有问题,所以让我们通过使用内省(introspection) API 来确定谁是对的。
BeanInfo info = Introspector.getBeanInfo(ClassTest.class);
for (PropertyDescriptor pd : info.getPropertyDescriptors()) {
System.out.println(pd.getName() + ": " + pd.getReadMethod() +
" : " + pd.getWriteMethod());
}
对于上面的代码,这会打印两种方法 - 即 Eclipse 是正确的,JSF 是错误的。但这对我来说听起来很可疑,因为the specification没有提到任何关于双"is"的事情。
但是在查看规范时,我看到了一些我从未使用过的东西——所谓的索引属性。您可以使用 private String[] bar
,然后使用 public String getBar(int idx)
。所以:
2。我用 Introspector
尝试过,但没有找到 bar 的读取方法。上述代码的结果是:bar: null : null
。所以我开始思考 - 现在内省(introspection)者不遵循规范。也许它在之前的案例中没有遵循它,最终,JSF 是正确的。事实上,索引属性可以使给定属性有两种读取方法。这对于内省(introspection) API 的 PropertyDescriptor
类是不可能的。
这将我们引向何方 - 我们有一个不符合规范的可能已损坏的 API。这导致规范的其他实现(JSF 显然使用自定义实现)。这导致了进一步的误解和困惑。
关于困扰我的事情的旁注 - 在 JavaBeans 规范中,他们将方法的命名约定称为“设计模式”。这对我来说听起来不对。
那么,现在进入问题:
更新。看起来 JSF 用法是 bean.isUrl
而不是 bean.url
。不使用 isUrl()
访问器是完全合理的。
附言JDK 1.6.0_20、JSF 1.2、MyFaces
最佳答案
Java Bean 属性由方法而不是字段定义。出于这个原因 PropertyDescriptor
类有getReadMethod()
和 getWriteMethod()
方法,但没有 getField()
方法。
就我个人而言,我认为您的同事使用了一种不好的做法。
a) is
是一个动词。字段不应以动词命名。
b) 虽然这不是必需的,但好的做法是像属性一样命名字段,这样您就可以编写如下代码:
PropertyDescriptor pd; // let's assume this is set
Method referenceMethod = pd.getReadMethod() == null
// at least one of these is not null
? pd.getWriteMethod() : pd.getReadMethod();
Field underLyingField = referenceMethod
.getDeclaringClass()
.getDeclaredField(pd.getName());
虽然此代码未标准化,但它遵循约定并且可以派上用场。如果您不遵循这样的约定,您将无法将字段与属性相关联(我知道这是故意的)。
例如我使用上面的代码来检查该字段是否有注释
关于索引属性:
您可以在数组或列表(或映射)属性上使用索引语法,但前提是它们被定义为标准 bean 属性。
所以如果你有这样的属性(property):
private String[] bar;
public String[] getBar(){
return bar;
}
public void setBar(String[] bar){
this.bar = bar;
}
或者像这样:
private List<String> bar;
public List<String> getBar(){
return bar;
}
public void setBar(List<String> bar){
this.bar = bar;
}
您可以使用表达式 ${bar[0]}
访问第一个成员
还有像这样的 map 属性:
private Map<String, String> bar;
public Map<String, String> getBar(){
return bar;
}
public void setBar(Map<String, String> bar){
this.bar = bar;
}
您可以像这样访问映射到 "baz"
的值 ${bar['baz']}
。
此功能建立在标准 beans 功能之上,因此它需要常规的 getter/setter。
关于JavaBeans 和内省(introspection) - 搞砸了 boolean 值和索引属性?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4708670/
你能比较一下属性吗 我想禁用文本框“txtName”。有两种方式 使用javascript,txtName.disabled = true 使用 ASP.NET, 哪种方法更好,为什么? 最佳答案 我
Count 属性 返回一个集合或 Dictionary 对象包含的项目数。只读。 object.Count object 可以是“应用于”列表中列出的任何集合或对
CompareMode 属性 设置并返回在 Dictionary 对象中比较字符串关键字的比较模式。 object.CompareMode[ = compare] 参数
Column 属性 只读属性,返回 TextStream 文件中当前字符位置的列号。 object.Column object 通常是 TextStream 对象的名称。
AvailableSpace 属性 返回指定的驱动器或网络共享对于用户的可用空间大小。 object.AvailableSpace object 应为 Drive 
Attributes 属性 设置或返回文件或文件夹的属性。可读写或只读(与属性有关)。 object.Attributes [= newattributes] 参数 object
AtEndOfStream 属性 如果文件指针位于 TextStream 文件末,则返回 True;否则如果不为只读则返回 False。 object.A
AtEndOfLine 属性 TextStream 文件中,如果文件指针指向行末标记,就返回 True;否则如果不是只读则返回 False。 object.AtEn
RootFolder 属性 返回一个 Folder 对象,表示指定驱动器的根文件夹。只读。 object.RootFolder object 应为 Dr
Path 属性 返回指定文件、文件夹或驱动器的路径。 object.Path object 应为 File、Folder 或 Drive 对象的名称。 说明 对于驱动器,路径不包含根目录。
ParentFolder 属性 返回指定文件或文件夹的父文件夹。只读。 object.ParentFolder object 应为 File 或 Folder 对象的名称。 说明 以下代码
Name 属性 设置或返回指定的文件或文件夹的名称。可读写。 object.Name [= newname] 参数 object 必选项。应为 File 或&
Line 属性 只读属性,返回 TextStream 文件中的当前行号。 object.Line object 通常是 TextStream 对象的名称。 说明 文件刚
Key 属性 在 Dictionary 对象中设置 key。 object.Key(key) = newkey 参数 object 必选项。通常是 Dictionary 
Item 属性 设置或返回 Dictionary 对象中指定的 key 对应的 item,或返回集合中基于指定的 key 的&
IsRootFolder 属性 如果指定的文件夹是根文件夹,返回 True;否则返回 False。 object.IsRootFolder object 应为&n
IsReady 属性 如果指定的驱动器就绪,返回 True;否则返回 False。 object.IsReady object 应为 Drive&nbs
FreeSpace 属性 返回指定的驱动器或网络共享对于用户的可用空间大小。只读。 object.FreeSpace object 应为 Drive 对象的名称。
FileSystem 属性 返回指定的驱动器使用的文件系统的类型。 object.FileSystem object 应为 Drive 对象的名称。 说明 可
Files 属性 返回由指定文件夹中所有 File 对象(包括隐藏文件和系统文件)组成的 Files 集合。 object.Files object&n
我是一名优秀的程序员,十分优秀!