方法引用是Java中的方法参数线程安全

时间:2017-01-27 14:52:06

标签: java multithreading thread-safety method-reference

我有以下情况:

1.3

我在像这样的“多线程”环境中使用它:

并发线程正在调用此方法

interface ValueBinding<T> {
    public void setValue(T input);
}

public enum FacesBinding {
    VALUE;
    public void bindString(ValueBinding<String> fcn, HttpServletRequest req, String param){
        try {
            String val = req.getParameter(param);
            if( val != null )
                fcn.setValue(val);
        } catch (Exception e) { }        
    }
    public void bindBoolean(ValueBinding<Boolean> fcn, HttpServletRequest req, String param){
        try {
            fcn.setValue(req.getParameter(param) != null);
        } catch (Exception e) { }        
    }
    public void bindInt(ValueBinding<Integer> fcn, HttpServletRequest req, String param){
        try {
            int val = Integer.parseInt(req.getParameter(param));
            fcn.setValue(val);
        } catch (Exception e) { }        
    }
    public void bindLong(ValueBinding<Long> fcn, HttpServletRequest req, String param){
        try {
            long val = Long.parseLong(req.getParameter(param));
            fcn.setValue(val);
        } catch (Exception e) { }        
    }
...
...
}

@Override // concurrent Threads are calling this method public Category initData(FacesContext facesContext) throws Exception { Category entity = new Category(); HttpServletRequest req = facesContext.getRequest(); FacesBinding.VALUE.bindLong(entity::setId, req, Table.Category.Field.ID.name()); FacesBinding.VALUE.bindString(entity::setName, req, Table.Category.Field.NAME.name()); FacesBinding.VALUE.bindInt(entity::setPosition, req, Table.Category.Field.POSITION.name()); FacesBinding.VALUE.bindBoolean(entity::setLocalized, req, Table.Category.Field.LOCALIZED.name()); return entity; }

方法参考(界面)FacesBinding.VALUE.bindLong(entity::setId, req, Table.Category.Field.ID.name());作为枚举对象中方法的参数传递时,

100%线程安全 (单身)?

注:

entity::setId

...等。所有这些方法都是标准的java setter方法

entity::setId

entity::setName

entity::setPosition

更新

具体:

public void setId(long id) {
        this.id = id;
    }
public void setName(String name) {
        this.name = name;
    }
....

100%等于

Category entity = new Category();
entity.setId(5);//thread safe for sure

事实上FacesBinding.VALUE.bindLong(entity::setId, ...); 是单身,而FacesBinding中的方法参考是否使线程不安全?

1 个答案:

答案 0 :(得分:1)

如果您的setId方法是线程安全的,那么您的方法引用调用将是线程安全的,仅此而已。

方法参考是创建ValueBinding对象的简洁速记。编译它们时,会有一个私有的内部类,它们实现了你的功能接口并调用你指定的方法。既然你指定了属于一个对象的方法,那么这个内部类也将等同于,它具有接受你的Category对象的构造函数,以及一个存储它的私有字段(我说相当于因为默认情况下,如果实现可以证明并选择任何其他行为,则实现不限于此行为。