Saturday, April 30, 2011

Writing a swap function in java

Method 1 : Changing the data underneath
public class Swapper<T> {
      public Swapper(T obj) {
             data_ = obj;
      }
      public T get() { return data_; }
      public void set(T value) { data_ = value; }
      public void swap(Swapper<T> o) {
           T tmp = o.data_;
           o.data_ = data_;
           data_ = tmp;
      }
      private T data_ = null;
  }

  // .. Now you can do:
  Swapper<String> a = new Swapper("Hello");
  Swapper<String> b = new Swapper("World");
  // a.get().equals("Hello")
  a.swap(b); // now a.get().equals("World")


But we can write function which uses the above idea:
public void Swap(RefObject<Integer> p, RefObject<Integer> q)
{
   int temp;
   temp = p.argvalue;
   p.argvalue = q.argvalue;
   q.argvalue = temp;
}
public final class RefObject<T>
{
    public T argvalue;
    public RefObject(T refarg)
    {
        argvalue = refarg;
    }
}


Method 2 : Using Atomic reference
Example for integers:

public void swap(AtomicInteger a, AtomicInteger b){
     a.set(b.getAndSet(a.get()));
}
  

Above method can be written in more verbose way like this:

import java.util.concurrent.atomic.AtomicInteger;
public class TestAtomicInteger{
    private static void swap(AtomicInteger a, AtomicInteger b) {
        int val = a.get();
        a.set(b.get());
        b.set(val);
    }

    public static void main(String[] args) {
        AtomicInteger a = new AtomicInteger(1);
        AtomicInteger b = new AtomicInteger(2);

        swap(a, b);

        System.out.println("a: " + a + " b: " + b);
    }
}

Example for strings:
public void swap(AtomicReference a, AtomicReference b){
        a.set(b.getAndSet(a.get()));
}


Of course this not very satisfactory, as you hardly ever develop against AtomicReferences. But basically you need to use some kind of container as shown above, because you can't just swap the references. So you can e.g. swap the elements of a two-element array or list, but you just can't swap two strings without having access to the original variables (so you can't do it in a helper function).

Case when data is in list:
If your data happens to be a List, a better way to swap is to use Collections.swap(List, int, int).
In above function following are the function and parameters:

Swaps the elements at the specified positions in the specified list.
(If the specified positions are equal, invoking this method leaves
the list unchanged.)
Parameters:
    list - The list in which to swap elements.
    i - the index of one element to be swapped.
    j - the index of the other element to be swapped. 

Case when swap is required in sorting:
apparently the real objective is to sort an array of ints. That's a one-liner with Arrays.sort(int[]):

int[] arr = {2,3,1,378,19,25};
Arrays.sort(arr);

To check the output:
   System.out.println(Arrays.toString(arr));
   // [1, 2, 3, 19, 25, 378]

And here is a simple helper function to swap two positions in an array of ints:

public static void swap(final int[] arr, final int pos1, final int pos2){
   final int temp = arr[pos1];
   arr[pos1] = arr[pos2];
   arr[pos2] = temp;
}

No comments:

Post a Comment

Chitika