RefCell copied/clonned difference

Not sure I can see the difference between copied and copied methods, eg:

self.index.borrow().get(key).cloned()
self.index.borrow().get(key).copied()

Found some answers here but can't ask there about RefCell context, because of subject was locked. This clone/copy always confusing me, as expecting reference clone semantics literally, but sometimes it's same, e.g. for String, where clone is just copy, even data stored on the heap.

They do the same thing.

The advantage of .copied() is that it only compiles if the operation is very cheap. This may be useful to improve clarity of the code to readers.

4 Likes

This is asking about methods of Option actually, isn't it? You're using something like RefCell<HashMap<K, V>>, so your method chain produces Ref<'_, HashMap<K, V>> then implicitly dereference to &HashMap<K, V>, then calls HashMap::get producing Option<&V> and finally calls Option<&T>'s copied or cloned method on that.

2 Likes

I'm not sure what you mean by "reference clone semantics literally". As for why a cloning a String is not considered a copy, it's because of the difference between copy and move semantics. Further down that page it says:

Copies happen implicitly, for example as part of an assignment y = x. The behavior of Copy is not overloadable; it is always a simple bit-wise copy.

Cloning is an explicit action, x.clone(). The implementation of Clone can provide any type-specific behavior necessary to duplicate values safely. For example, the implementation of Clone for String needs to copy the pointed-to string buffer in the heap. A simple bitwise copy of String values would merely copy the pointer, leading to a double free down the line. For this reason, String is Clone but not Copy.

The Book has a graphical presentation of the String example.

(Moving is also always a notional bit-wise copy, but leaves the source in an uninitialized state.)

1 Like