【问题标题】:Passing existing array gives different results than passing new array with elements out of that array传递现有数组与传递具有该数组外元素的新数组相比,会产生不同的结果
【发布时间】:2014-11-29 07:15:01
【问题描述】:

我正在为 Android 编写游戏。游戏元素的颜色是通过存储 RGBA 值的 ColorTheme 对象设置的。 在初始化例如一个三角形,一个带有 RGBA 值的数组,来自 ColorTheme 对象,正被传递给构造函数。 虽然 ColorTheme-Object 中的颜色在初始化后永远不会改变,但三角形的颜色会改变。我试图找出原因。 我注意到,如果我通过 ColorTheme-Array 中的元素传递一个新数组,而不是将 ColorTheme 对象本身传递给 Triangle 构造函数,它就像我想要的那样工作。这真的无关紧要,因为 Java 中没有指针之类的东西(对吗?)。

@Override
public void onSurfaceChanged(GL10 gl10, int width, int height) {

//...

mThemes = new ColorTheme[]{
            new ColorTheme(
                    new float[]{0.20f, 0.71f, 0.91f, 1.00f},    // blue circle
                    new float[]{1.00f, 1.00f, 1.00f, 1.00f},    // white obstacle
                    new float[]{1.00f, 1.00f, 1.00f, 1.00f},    // white triangle
                    new float[]{0.00f, 0.60f, 0.80f, 1.00f}     // shadow
            ),
            new ColorTheme(
                    new float[]{0.27f, 0.40f, 0.80f, 1.00f},    // purple circle
                    new float[]{1.00f, 1.00f, 1.00f, 1.00f},    // white obstacle
                    new float[]{1.00f, 1.00f, 1.00f, 1.00f},    // white triangle
                    new float[]{0.60f, 0.20f, 0.80f, 1.00f}     // shadow
            ),
            new ColorTheme(
                    new float[]{0.60f, 0.80f, 0.00f, 1.00f},    // green circle
                    new float[]{1.00f, 1.00f, 1.00f, 1.00f},    // white obstacle
                    new float[]{1.00f, 1.00f, 1.00f, 1.00f},    // white triangle
                    new float[]{0.40f, 0.60f, 0.00f, 1.00f}     // shadow
            )
    };

//...

// Values keep changing after initialization like this    
mShadowTriangle = new Triangle(mScreenRatio, mThemes[outerThemeIndex].theme[3],true);

// They don't like this 
mShadowTriangle = new Triangle(mScreenRatio, new float[]{mThemes[outerThemeIndex].theme[3][0],mThemes[outerThemeIndex].theme[3][1],mThemes[outerThemeIndex].theme[3][2],mThemes[outerThemeIndex].theme[3][3]},true);
}

【问题讨论】:

    标签: java android arrays


    【解决方案1】:

    Java 数组,甚至是基元数组,都是Objects。因此,如果您不传递副本(使用您的方法或Arrays.copyOf() 方法之一),那么对原始参考的更改将修改您的Object 参考。

    【讨论】:

      【解决方案2】:

      没有指针这种东西本身,但是仍然有对象引用,它们的作用就像指针(除了它们不允许指针算术)。这意味着两者之间的世界不同

      new Blah(x);
      

      new Blah(copyOfX);
      

      每次,如果这些是我们正在讨论的对象,它们都会通过引用传递。这意味着如果Blah 的构造函数决定对传递给它的对象进行修改,那么第一个将最终修改x,但第二个不会,因为只有副本会修改。

      底线是,如果您有一个不想弄乱的数组,并且您将它传递给可能会修改它所获得的数组的代码,那么您希望传递一个克隆而不是原始数组。

      如果你有一组原语(比如int[]),你可以使用

      int[] copyOfX = Arrays.copyOf(x, x.length);
      

      获取克隆。请注意,如果数组的元素本身就是对象,那么这将为您提供 浅拷贝(然后您需要查找浅拷贝和深拷贝之间的区别) .

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2013-10-27
        • 2014-07-05
        • 2014-09-28
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-09-24
        相关资源
        最近更新 更多