How to overcome the fact that primitives are passed by value

前提是你 提交于 2019-12-10 17:16:07

问题


I have a long piece of code that calculates two values (doubles) for me, I use this piece of code in a few places - to stick with DRY principles I should refactor this bit of code to a nice unit testable method. However I cant make it return two doubles, and doubles are primitive so cannot be passed by value and manipulated. The cleanest way I can think of doing this is by making this method return an double[]. Can anyone think of a better way?

Thanks


回答1:


Firstly, all variables are passed by value in Java, not just primitives. It's just that objects can be mutable. It's important to understand that. For example:

public void addHour(Date date) {
  date.setTime(date.getTime() + 3600 * 1000);
}

The date is passed by value but Date is mutable so it can be modified but try and do this:

public void addHour(Date date) {
  date = new Date(date.getTime() + 3600 * 1000);
}

and it won't change the date. Why? Because date is a reference but is passed by value.

Secondly, do these doubles relate to each other in some way? If so wrap them in a class than describes this relationship like:

public class Coordinate {
  private final double x;
  private final double y;

  public Coordinate(double x, double y) {
    this.x = x;
    this.y = y;
  }

  public double getX() { return x; }
  public double getY() { return y; }
}



回答2:


You could encapsulate them in a class for this purpose.

You could also give a double[] parameter to the method that calculates them and where it will put the calculated values in. This can be rather efficent as the caller code can reuse this array for successive invocations if performance is important.




回答3:


A class (immutable) with two double fields? Might even want to add some interesting methods to the class.

The other way around is to have the method take a callback object.




回答4:


double[] arr = {val1, val2};
return arr

or go with a Pair-like class that encapsulates 2 values...




回答5:


If the two doubles can be thought of as a logical pairing of values, then it might make sense to bundle them in a simple object?




回答6:


I'm more of a C++ guy, but creating an object of your own called Pair which can hold 2 doubles and can be passed by reference makes sense to me.




回答7:


Create an new class that has two double properties with getters and setters and constructor if you like (and equals and hashcode...) and make the method return that type of object. A generic way to do that would be a Pair class. This is a common pattern and you should find code snippets everywhere (e.g. in the netbeans code base).




回答8:


You have several options:

  1. Return an array
  2. Return a List<double>
  3. Return an object of a class that wraps your two doubles

And by the way, Java does not pass objects by reference. It passes pointers to objects by value. http://javadude.com/articles/passbyvalue.htm




回答9:


A double array is the most obvious answer. You can make it a bit safer by having a wrapper object like this:

  public class MyTwoDoubles {

       public MyTwoDoubles(double one, double two) { ... }

       public double getOne() { ... }

       public double getTwo() { ... }
  }



回答10:


You can rather use Wrapper classes which are of reference types For every value type you can find a wrapper class. for your case java.lang.Double can be used,hope this solves the purpose But still as a good design i suggest you not to alter the object value inside the method. Instead refactor the code in such a way you call it twice and return two different values then assign it to the original. As a good practice its not advisible to alter object value inside a method



来源:https://stackoverflow.com/questions/2113656/how-to-overcome-the-fact-that-primitives-are-passed-by-value

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!