作为参数传递的对象不会创建多个实例

时间:2015-04-19 07:52:38

标签: java multithreading static multiple-instances pass-by-value

我在我的程序中处理多线程。 该对象作为值传递。但是我注意到,当作为参数传递时,该对象不会创建另一个实例。

我正在使用多线程,其中在被调用的方法中,我正在更改变量的值(属于作为参数传递的对象),并且在调用方法中,变量也会更改。

Class_1
{
  Public Static void main()
  {
    SomeObject obj=new SomeObject();
    Class_2 class_2=new Class_2();
    obj.setVar1(someValue) 
    class_2.method_2(obj)
    thread.sleep(5000)   // --> Till then the method_2() gets executed
    system.out.println(obj.getVar1)  // --> Also prints someAnotherValue (SHOULD PRINT someValue)
  }
}

Class_2
{
  method_2(SomeObject obj)  // --> non static method
  {
    obj.setVar1(someAnotherValue)
    system.out.println(obj.getVar1)  // --> Print someAnotherValue
  }
}

我一直在想,作为参数传递的对象会创建另一个实例。 我希望我的对象在传递时创建另一个实例。有可能吗?

如果需要,我可以再解释一下。

更新:

示例Bean类

public class IngestionBean {
    private String stageDDL;

    public String getStageDDL() {
        return stageDDL;
    }

    public void setStageDDL(String stageDDL) {
        this.stageDDL = stageDDL;
    }
}   

ArchiveMain类

这里for循环中的数据进入线程。

public class ArchiveMain
{
    public static void main(String args[]) throws IOException, InterruptedException
    {
    IngestionBean ingestionBean = new IngestionBean();
    ArchivingData archivingData;

    //..

    //----- ArchivingData is threaded class, will be called multiple times
    //----- Assume dataFile.length = 2
    for (int i = 0; i < dataFile.length; i++)
    {
        archivingData = new ArchivingData(ingestionBean, dataFile[i], ddlFile[i], i);
        archivingData.start();
    }

    //..    
    }
}   

ArchivingData类

正在更改stageDDL的每个线程值 - 在run()

public class ArchivingData implements Runnable
{
    private HiveDao hiveDao = new HiveDao();
    private IngestionBean ingestionBean = new IngestionBean();
    public ArchivingData(IngestionBean ingestionBean, String dataFile, String ddlFile, Integer i)
    {
    this.ingestionBean = ingestionBean;
    this.dataFile = dataFile;
    this.ddlFile = ddlFile;
    }

    public void run()
    {
    //.. 
    String stageTableName = dataFile.replace("-", "_").replace(".", "_");

    //---- Changing the value of stageDDL in IngestionBean class in every new thread
    //---- Second thread is called instantly after the first thread
    ingestionBean.setStageDDL(ddlFilePath.toString());          

    //---- passing ingestionBean object
    Boolean stageTableStatus = hiveDao.createStageTable(ingestionBean, stageTableName, intvalue);    

    //..
    }

    public void start() throws InterruptedException
    {
    LOGGER.info("Starting thread for datafile: " + dataFile);
    if (thread == null)
    {
        thread = new Thread(this, dataFile);
        thread.start();
    }
    }
}

HiveDao班

由于涉及的操作不多,所有线程同时到达createStageTable 并且线程将具有相同的stageDDL值(因为只创建了一个ingestionBean对象实例)

public class HiveDao
{
    public Boolean createStageTable(IngestionBean ingestionBean)
    {
    //---- Don't receive unique value of stageDDL here
    //---- Always receive the latest value of stageDDL (modified in run() )
    //---- It is not creating another instance of ingestionBean object. Using the same instance created in main()
    statement.executeUpdate(ingestionBean.getStageDDL);     
    }
}

我希望在将对象传递给for循环中的ArchivingData之后创建新的ingestionBean对象实例。 是否可能

2 个答案:

答案 0 :(得分:4)

Java将引用传递给对象,而不是对象。如果你想要另一个实例,那么在调用方法之前创建一个实例。

PS:当你发布代码时,发布真正的代码,而不是用你想象的语言代码。还要尊重Java命名约定。另外,我不想变得粗鲁,但多线程是一个非常非常困难的主题,在考虑多线程之前,你最好先了解Java和OO的基础知识。

答案 1 :(得分:-1)

Java传递引用。

最简单的方法是克隆对象..如果它在实际实现中有意义http://docs.oracle.com/javase/7/docs/api/java/lang/Object.html#clone()