我对java多线程有疑问。
我有一个可以访问多个线程的类。
Class A
{
private Object obj;
public Object returnObject()
{
if(condition)
return getObjectA();
else
return getObjectB();
}
public Object getObjectA()
{
obj = new Object()
obj.setProperty("prp1");
}
public Object getObjectB()
{
obj = new Object()
obj.setProperty("prp2");
}
}
当有多个线程访问getObj ..()时。它是否会产生“obj”状态的问题。会有不良后果吗?
谢谢SLaks和Peter,
我认为以下内容也将解决线程安全问题:
public Object getObjectA()
{
Object obj = new Object()
obj.setProperty("prp1");
return obj;
}
答案 0 :(得分:0)
是
如果两个线程同时在returnObject()
中调用不同的代码路径,它可以在getObjectB()
中的两个语句之间运行getObjectA()
,最后在ObjectB上调用obj.setProperty("prp1");
。
答案 1 :(得分:0)
是的,它会产生问题(尝试代码看看会出现什么样的问题,但数据会丢失)。
最简单的解决方案是使用synchronized
块。
答案 2 :(得分:0)
提供,if(true)
不是硬编码的,因为这将修复始终调用getObjA()的执行路径!
是的,此代码可能会遇到竞争条件,其中obj
的值可能取决于线程执行的顺序(即多个线程调用getObj ..()的顺序)。
您需要synchronize
访问obj变量。
答案 3 :(得分:0)
我认为getObjectA()
和getObjectB()
应该声明为私有,然后你应该在returnObject()
方法中使用synchronized块,所以像这样:
class A
{
private Object obj;
public Object returnObject()
{
Object result;
synchronized (A.class) {
result = (true) ? getObjectA() : getObjectB();
}
return result;
}
private Object getObjectA()
{
obj = new Object()
obj.setProperty("prp1");
}
private Object getObjectB()
{
obj = new Object()
obj.setProperty("prp2");
}
}
显然 true 条件必须替换为某些条件......
答案 4 :(得分:0)
我建议将代码更改为 NOT 将“obj
”保存为数据成员,因为它需要同时访问。
有几种解决方案:
clone()
并进行编辑。答案 5 :(得分:0)
是的,但这很容易修复,因为你每次调用都会替换obj
,你显然不关心它,所以尝试使字段obj
只是一个局部变量,如这样:
Class A {
public Object returnObject() {
if (true)
return getObjectA();
return getObjectB();
}
public Object getObjectA() {
Object obj = new Object()
obj.setProperty("prp1");
return obj;
}
public Object getObjectB() {
Object obj = new Object()
obj.setProperty("prp2");
return obj;
}
}
如果这适合您,请考虑制作这些方法static
。