diff --git a/redisson/src/main/java/org/redisson/RedissonAtomicDouble.java b/redisson/src/main/java/org/redisson/RedissonAtomicDouble.java
index 61ceba620..e23d67c23 100644
--- a/redisson/src/main/java/org/redisson/RedissonAtomicDouble.java
+++ b/redisson/src/main/java/org/redisson/RedissonAtomicDouble.java
@@ -60,7 +60,8 @@ public class RedissonAtomicDouble extends RedissonExpirable implements RAtomicDo
     @Override
     public RFuture<Boolean> compareAndSetAsync(double expect, double update) {
         return commandExecutor.evalWriteAsync(getName(), StringCodec.INSTANCE, RedisCommands.EVAL_BOOLEAN,
-                "if tonumber(redis.call('get', KEYS[1])) == tonumber(ARGV[1]) then "
+                  "local value = redis.call('get', KEYS[1]);"
+                + "if (value == false and tonumber(ARGV[1]) == 0) or (tonumber(value) == tonumber(ARGV[1])) then "
                      + "redis.call('set', KEYS[1], ARGV[2]); "
                      + "return 1 "
                    + "else "
@@ -80,12 +81,26 @@ public class RedissonAtomicDouble extends RedissonExpirable implements RAtomicDo
 
     @Override
     public double get() {
-        return addAndGet(0);
+        return get(getAsync());
     }
 
+    @Override
+    public double getAndDelete() {
+        return get(getAndDeleteAsync());
+    }
+    
+    @Override
+    public RFuture<Double> getAndDeleteAsync() {
+        return commandExecutor.evalWriteAsync(getName(), StringCodec.INSTANCE, RedisCommands.EVAL_DOUBLE,
+                   "local currValue = redis.call('get', KEYS[1]); "
+                 + "redis.call('del', KEYS[1]); "
+                 + "return currValue; ",
+                Collections.<Object>singletonList(getName()));
+    }
+    
     @Override
     public RFuture<Double> getAsync() {
-        return addAndGetAsync(0);
+        return commandExecutor.writeAsync(getName(), StringCodec.INSTANCE, RedisCommands.GET_DOUBLE, getName());
     }
 
     @Override
diff --git a/redisson/src/main/java/org/redisson/RedissonAtomicLong.java b/redisson/src/main/java/org/redisson/RedissonAtomicLong.java
index 69b8bb647..22d65d1f2 100644
--- a/redisson/src/main/java/org/redisson/RedissonAtomicLong.java
+++ b/redisson/src/main/java/org/redisson/RedissonAtomicLong.java
@@ -66,6 +66,20 @@ public class RedissonAtomicLong extends RedissonExpirable implements RAtomicLong
                    + "end",
                 Collections.<Object>singletonList(getName()), expect, update);
     }
+    
+    @Override
+    public long getAndDelete() {
+        return get(getAndDeleteAsync());
+    }
+    
+    @Override
+    public RFuture<Long> getAndDeleteAsync() {
+        return commandExecutor.evalWriteAsync(getName(), StringCodec.INSTANCE, RedisCommands.EVAL_LONG_SAFE,
+                   "local currValue = redis.call('get', KEYS[1]); "
+                 + "redis.call('del', KEYS[1]); "
+                 + "return currValue; ",
+                Collections.<Object>singletonList(getName()));
+    }
 
     @Override
     public long decrementAndGet() {
@@ -79,12 +93,12 @@ public class RedissonAtomicLong extends RedissonExpirable implements RAtomicLong
 
     @Override
     public long get() {
-        return addAndGet(0);
+        return get(getAsync());
     }
 
     @Override
     public RFuture<Long> getAsync() {
-        return addAndGetAsync(0);
+        return commandExecutor.writeAsync(getName(), StringCodec.INSTANCE, RedisCommands.GET_LONG, getName());
     }
 
     @Override
diff --git a/redisson/src/main/java/org/redisson/api/RAtomicDouble.java b/redisson/src/main/java/org/redisson/api/RAtomicDouble.java
index e52b395dc..7ec2abcb5 100644
--- a/redisson/src/main/java/org/redisson/api/RAtomicDouble.java
+++ b/redisson/src/main/java/org/redisson/api/RAtomicDouble.java
@@ -62,6 +62,13 @@ public interface RAtomicDouble extends RExpirable, RAtomicDoubleAsync {
      * @return the current value
      */
     double get();
+    
+    /**
+     * Gets and deletes object
+     * 
+     * @return the current value
+     */
+    double getAndDelete();
 
     /**
      * Atomically adds the given value to the current value.
diff --git a/redisson/src/main/java/org/redisson/api/RAtomicDoubleAsync.java b/redisson/src/main/java/org/redisson/api/RAtomicDoubleAsync.java
index d83dbf883..9889655ab 100644
--- a/redisson/src/main/java/org/redisson/api/RAtomicDoubleAsync.java
+++ b/redisson/src/main/java/org/redisson/api/RAtomicDoubleAsync.java
@@ -15,6 +15,11 @@
  */
 package org.redisson.api;
 
+/**
+ * 
+ * @author Nikita Koksharov
+ *
+ */
 public interface RAtomicDoubleAsync extends RExpirableAsync {
 
     RFuture<Boolean> compareAndSetAsync(double expect, double update);
@@ -25,6 +30,13 @@ public interface RAtomicDoubleAsync extends RExpirableAsync {
 
     RFuture<Double> getAsync();
 
+    /**
+     * Gets and deletes object
+     * 
+     * @return the current value
+     */
+    RFuture<Double> getAndDeleteAsync();
+    
     RFuture<Double> getAndAddAsync(double delta);
 
     RFuture<Double> getAndSetAsync(double newValue);
diff --git a/redisson/src/main/java/org/redisson/api/RAtomicLong.java b/redisson/src/main/java/org/redisson/api/RAtomicLong.java
index 714f56fcb..c2d8da378 100644
--- a/redisson/src/main/java/org/redisson/api/RAtomicLong.java
+++ b/redisson/src/main/java/org/redisson/api/RAtomicLong.java
@@ -63,6 +63,13 @@ public interface RAtomicLong extends RExpirable, RAtomicLongAsync {
      */
     long get();
 
+    /**
+     * Gets and deletes object
+     * 
+     * @return the current value
+     */
+    long getAndDelete();
+    
     /**
      * Atomically adds the given value to the current value.
      *
diff --git a/redisson/src/main/java/org/redisson/api/RAtomicLongAsync.java b/redisson/src/main/java/org/redisson/api/RAtomicLongAsync.java
index 02bffedbd..c4cf387d1 100644
--- a/redisson/src/main/java/org/redisson/api/RAtomicLongAsync.java
+++ b/redisson/src/main/java/org/redisson/api/RAtomicLongAsync.java
@@ -15,6 +15,11 @@
  */
 package org.redisson.api;
 
+/**
+ * 
+ * @author Nikita Koksharov
+ *
+ */
 public interface RAtomicLongAsync extends RExpirableAsync {
 
     RFuture<Boolean> compareAndSetAsync(long expect, long update);
@@ -24,6 +29,13 @@ public interface RAtomicLongAsync extends RExpirableAsync {
     RFuture<Long> decrementAndGetAsync();
 
     RFuture<Long> getAsync();
+    
+    /**
+     * Gets and deletes object
+     * 
+     * @return the current value
+     */
+    RFuture<Long> getAndDeleteAsync();
 
     RFuture<Long> getAndAddAsync(long delta);
 
diff --git a/redisson/src/main/java/org/redisson/client/protocol/RedisCommands.java b/redisson/src/main/java/org/redisson/client/protocol/RedisCommands.java
index 48299979a..c3eac37eb 100644
--- a/redisson/src/main/java/org/redisson/client/protocol/RedisCommands.java
+++ b/redisson/src/main/java/org/redisson/client/protocol/RedisCommands.java
@@ -32,6 +32,7 @@ import org.redisson.client.protocol.convertor.BooleanNullReplayConvertor;
 import org.redisson.client.protocol.convertor.BooleanNullSafeReplayConvertor;
 import org.redisson.client.protocol.convertor.BooleanNumberReplayConvertor;
 import org.redisson.client.protocol.convertor.BooleanReplayConvertor;
+import org.redisson.client.protocol.convertor.DoubleNullSafeReplayConvertor;
 import org.redisson.client.protocol.convertor.DoubleReplayConvertor;
 import org.redisson.client.protocol.convertor.IntegerReplayConvertor;
 import org.redisson.client.protocol.convertor.KeyValueConvertor;
@@ -133,7 +134,7 @@ public interface RedisCommands {
     RedisCommand<List<ScoredEntry<Object>>> ZRANGE_ENTRY = new RedisCommand<List<ScoredEntry<Object>>>("ZRANGE", new ScoredSortedSetReplayDecoder<Object>());
     RedisCommand<List<ScoredEntry<Object>>> ZRANGEBYSCORE_ENTRY = new RedisCommand<List<ScoredEntry<Object>>>("ZRANGEBYSCORE", new ScoredSortedSetReplayDecoder<Object>());
     RedisCommand<ListScanResult<Object>> ZSCAN = new RedisCommand<ListScanResult<Object>>("ZSCAN", new ListMultiDecoder(new LongMultiDecoder(), new ScoredSortedSetScanDecoder<Object>(), new ScoredSortedSetScanReplayDecoder()));
-    RedisStrictCommand<Double> ZINCRBY = new RedisStrictCommand<Double>("ZINCRBY", new DoubleReplayConvertor());
+    RedisStrictCommand<Double> ZINCRBY = new RedisStrictCommand<Double>("ZINCRBY", new DoubleNullSafeReplayConvertor());
 
     RedisCommand<ListScanResult<String>> SCAN = new RedisCommand<ListScanResult<String>>("SCAN", new ListMultiDecoder(new LongMultiDecoder(), new ObjectListReplayDecoder<String>(), new ListScanResultReplayDecoder()));
     RedisStrictCommand<String> RANDOM_KEY = new RedisStrictCommand<String>("RANDOMKEY", new StringDataDecoder());
@@ -221,7 +222,9 @@ public interface RedisCommands {
     RedisStrictCommand<String> EVAL_STRING = new RedisStrictCommand<String>("EVAL", new StringReplayDecoder());
     RedisStrictCommand<String> EVAL_STRING_DATA = new RedisStrictCommand<String>("EVAL", new StringDataDecoder());
     RedisStrictCommand<Integer> EVAL_INTEGER = new RedisStrictCommand<Integer>("EVAL", new IntegerReplayConvertor());
+    RedisStrictCommand<Double> EVAL_DOUBLE = new RedisStrictCommand<Double>("EVAL", new DoubleNullSafeReplayConvertor());
     RedisStrictCommand<Long> EVAL_LONG = new RedisStrictCommand<Long>("EVAL");
+    RedisStrictCommand<Long> EVAL_LONG_SAFE = new RedisStrictCommand<Long>("EVAL", new LongReplayConvertor());
     RedisStrictCommand<Void> EVAL_VOID = new RedisStrictCommand<Void>("EVAL", new VoidReplayConvertor());
     RedisCommand<List<Object>> EVAL_LIST = new RedisCommand<List<Object>>("EVAL", new ObjectListReplayDecoder<Object>());
     RedisCommand<Set<Object>> EVAL_SET = new RedisCommand<Set<Object>>("EVAL", new ObjectSetReplayDecoder<Object>());
@@ -235,7 +238,7 @@ public interface RedisCommands {
 
     RedisStrictCommand<Long> INCR = new RedisStrictCommand<Long>("INCR");
     RedisStrictCommand<Long> INCRBY = new RedisStrictCommand<Long>("INCRBY");
-    RedisStrictCommand<Double> INCRBYFLOAT = new RedisStrictCommand<Double>("INCRBYFLOAT", new DoubleReplayConvertor());
+    RedisStrictCommand<Double> INCRBYFLOAT = new RedisStrictCommand<Double>("INCRBYFLOAT", new DoubleNullSafeReplayConvertor());
     RedisStrictCommand<Long> DECR = new RedisStrictCommand<Long>("DECR");
 
     RedisStrictCommand<Void> AUTH = new RedisStrictCommand<Void>("AUTH", new VoidReplayConvertor());
@@ -281,6 +284,7 @@ public interface RedisCommands {
     RedisCommand<Object> GET = new RedisCommand<Object>("GET");
     RedisStrictCommand<Long> GET_LONG = new RedisStrictCommand<Long>("GET", new LongReplayConvertor());
     RedisStrictCommand<Integer> GET_INTEGER = new RedisStrictCommand<Integer>("GET", new IntegerReplayConvertor());
+    RedisStrictCommand<Double> GET_DOUBLE = new RedisStrictCommand<Double>("GET", new DoubleNullSafeReplayConvertor());
     RedisCommand<Object> GETSET = new RedisCommand<Object>("GETSET");
     RedisCommand<Object> GETRANGE = new RedisCommand<Object>("GETRANGE");
     RedisCommand<Object> APPEND = new RedisCommand<Object>("APPEND");
diff --git a/redisson/src/main/java/org/redisson/client/protocol/convertor/DoubleNullSafeReplayConvertor.java b/redisson/src/main/java/org/redisson/client/protocol/convertor/DoubleNullSafeReplayConvertor.java
new file mode 100644
index 000000000..c1c0b1c5c
--- /dev/null
+++ b/redisson/src/main/java/org/redisson/client/protocol/convertor/DoubleNullSafeReplayConvertor.java
@@ -0,0 +1,19 @@
+package org.redisson.client.protocol.convertor;
+
+/**
+ * 
+ * @author Nikita Koksharov
+ *
+ */
+public class DoubleNullSafeReplayConvertor extends DoubleReplayConvertor {
+
+    @Override
+    public Double convert(Object obj) {
+        Double r = super.convert(obj);
+        if (r == null) {
+            return 0.0;
+        }
+        return r;
+    }
+    
+}
diff --git a/redisson/src/test/java/org/redisson/RedissonAtomicDoubleTest.java b/redisson/src/test/java/org/redisson/RedissonAtomicDoubleTest.java
index 3a4850ca0..0d69e2186 100644
--- a/redisson/src/test/java/org/redisson/RedissonAtomicDoubleTest.java
+++ b/redisson/src/test/java/org/redisson/RedissonAtomicDoubleTest.java
@@ -9,6 +9,23 @@ import org.redisson.api.RAtomicDouble;
 
 public class RedissonAtomicDoubleTest extends BaseTest {
 
+    @Test
+    public void testGetZero() {
+        RAtomicDouble ad2 = redisson.getAtomicDouble("test");
+        assertThat(ad2.get()).isZero();
+    }
+    
+    @Test
+    public void testGetAndDelete() {
+        RAtomicDouble al = redisson.getAtomicDouble("test");
+        al.set(10.34);
+        assertThat(al.getAndDelete()).isEqualTo(10.34);
+        assertThat(al.isExists()).isFalse();
+
+        RAtomicDouble ad2 = redisson.getAtomicDouble("test2");
+        assertThat(ad2.getAndDelete()).isZero();
+    }
+    
     @Test
     public void testCompareAndSet() {
         RAtomicDouble al = redisson.getAtomicDouble("test");
diff --git a/redisson/src/test/java/org/redisson/RedissonAtomicLongTest.java b/redisson/src/test/java/org/redisson/RedissonAtomicLongTest.java
index a35ff024f..170368e51 100644
--- a/redisson/src/test/java/org/redisson/RedissonAtomicLongTest.java
+++ b/redisson/src/test/java/org/redisson/RedissonAtomicLongTest.java
@@ -1,11 +1,30 @@
 package org.redisson;
 
+import static org.assertj.core.api.Assertions.assertThat;
+
 import org.junit.Assert;
 import org.junit.Test;
 import org.redisson.api.RAtomicLong;
 
 public class RedissonAtomicLongTest extends BaseTest {
 
+    @Test
+    public void testGetZero() {
+        RAtomicLong ad2 = redisson.getAtomicLong("test");
+        assertThat(ad2.get()).isZero();
+    }
+    
+    @Test
+    public void testGetAndDelete() {
+        RAtomicLong al = redisson.getAtomicLong("test");
+        al.set(10);
+        assertThat(al.getAndDelete()).isEqualTo(10);
+        assertThat(al.isExists()).isFalse();
+
+        RAtomicLong ad2 = redisson.getAtomicLong("test2");
+        assertThat(ad2.getAndDelete()).isZero();
+    }
+    
     @Test
     public void testCompareAndSetZero() {
         RAtomicLong al = redisson.getAtomicLong("test");