[concurrency-interest] BigDecimal Safe Publication

Florian Binder java at java4.info
Sun Aug 26 07:05:57 EDT 2012


I think the problem is with the constructor:

     public String(String original) {
         this.value = original.value;
         this.hash = original.hash;
     }

Since value is final, but hash not, it could happen that thread A is 
creating the string and thread B calls hashCode() before the hash is 
set. If you would not have the local variable h it could happen that 
thread A writes the hash while thread B is calculating it (is in the for 
loop). This would lead to a random hash.
But is not the compiler allowed to replace the local variable h with the 
field hash, since this does not change intra-thread semantic?

Regards,
Flo


Am 26.08.2012 12:27, schrieb Per Mildner:
> On Aug 20, 2012, at 7:58 PM, Zhong Yu <zhong.j.yu at gmail.com> wrote:
>
>> On Mon, Aug 20, 2012 at 6:49 AM, James <james at inaseq.com> wrote:
>>> I have a system that processes a lot of Doubles.  From time to time I need
>>> the accuracy of BigDecimal math but creating a BigDecimal is relatively
>>> expensive so I only do it when needed.  Hence I use lazy initialization as
>>> shown below.
>>>
>>> private Double price;  // although not final is effectively immutable and
>>> guaranteed non-null when used below
>>> private transient BigDecimal priceBD;
>>>
>>> public BigDecimal getPriceBD() {
>>> if (priceBD == null) {
>>> priceBD = BigDecimal.valueOf(price);  // strict singleton semantics not
>>> required
>>> }
>>> return priceBD;
>>> }
>> You may have omitted it for brevity, but a local variable is necessary
>> here for correctness. See String.hashCode()
> Where, and why, would a local variable help?
>
> Also, I do not see how this relates to String.hashCode().
>
> What am I missing?
>
> For reference, String.java:
> {
>      ...
>      private int hash; // Default to 0
>      ...
>      public int hashCode() {
>          int h = hash;
>          if (h == 0 && count > 0) {
>              int off = offset;
>              char val[] = value;
>              int len = count;
>
>              for (int i = 0; i < len; i++) {
>                  h = 31*h + val[off++];
>              }
>              hash = h;
>          }
>          return h;
>      }
>    ...
> }
>
> Regards,
>
> Per Mildner
> Per.Mildner at sics.se
>
>
>
> _______________________________________________
> Concurrency-interest mailing list
> Concurrency-interest at cs.oswego.edu
> http://cs.oswego.edu/mailman/listinfo/concurrency-interest



More information about the Concurrency-interest mailing list