I just upgraded to Stata 16 today and I was experimenting with the new frames feature. This allows a person to make changes to their data and then restore the original dataset. This is useful for e.g. robustness tests in which you want to drop observations or switch an indicator, run a regression, and then restore the original data.

Working with frames helped me come up with some code I personally found useful, and which I didn't find online anywhere else. So I'd thought I'd share it here, so that it shows up in a Google search for anyone else it might help.

I was attracted by the fact that you can refer to a frame by a descriptive name, so that you aren't likely to accidentally load the wrong data.

But I quickly realized a shortcoming in frames: any changes to the working data actually change the data in the frame. That is, the frame is mutable. So you have to make sure to constantly copy one frame to a new one and make changes to the new frame. It's easy to accidentally make changes to the current frame and thus affect all subsequent regressions in unintentional ways.

So that brought me back to snapshot, which is immutable. Once you make a snapshot, that snapshot is read-only. If you change any data, you are changing only the working data, not the snapshot. So if you restore the snapshot, all your changes are undone.

The one shortcoming of snapshot is that you have to refer to snapshots by number, not by name. This means it is easy to accidentally load the wrong snapshot. This can happen if you modify your code to create new snapshots and you forget to update all the numbers in your code.

But that helped me realize a way to refer to snapshots by name, not by number. This way, you get the immutability of snapshots but the descriptive names of frames. I thought I'd share the code, in case it helps anyone else.

The most important part is using "quietly snapshot list" followed by "global descriptive_name = r(snapshot)". r(snapshot) is the number of snapshots, so if you've just created a new snapshot, its number is equal to r(snapshot). Subsequently, you can restore the snapshot by executing "snapshot restore $descriptive_name" instead of "snapshot restore #".

Code:
* First snapshot
clear
cd "insert your path here"
use "insert your data file here"
* do various data processing, as required
snapshot save, label("First snapshot)
quietly snapshot list
global first_snapshot = r(snapshot)

* Second snapshot
clear
cd "insert your path here"
use "insert your data file here"
* do various data processing, as required
snapshot save, label("Second snapshot)
quietly snapshot list
global second_snapshot = r(snapshot)

* Visual inspection to verify
snapshot list
macro list

. . . 
clear
snapshot restore $first_snapshot
clear
snapshot restore $second_snapshot