When you need more structured management of annotations or overlays, you want to consider introducing a separate set of data structures to represent your organizational model (similarly to how one would manage a UITableView data source). A helper object or subclass of MKMapView can work; I prefer the former.
In your case, perhaps an array of arrays would work. The top level array represents each logical "layer". Each element in this array is an array of the overlays at that layer. These data structures should be owned, as private members, of your helper class, along with a weak reference or outlet to the MKMapView object. Provide methods to add/remove overlays, e.g. addOverlay:atLayer:
and removeOverlay:
, or pluralized variants that accept arrays of overlays. The helper class would first add the given overlays to the appropriate "layer" sub-array. Then, by adding up the counts of the arrays at the other layers, it can calculate the correct index value to use in the insertOverlay:atIndex:
message you send to the MKMapView.
I don't think there will be any significant hit on performance or memory usage.
By having a separate helper class instead of a subclass of MKMapView or embedding the code inside your view controller, it can be easier to reuse this in multiple view controllers, and it can also be easier to unit test.