substitute needs to iterate over the partition forests and skeletons of trees. Currently, these are constructed on the fly each time substitute is called. Since this is likely the most expensive part, it might make sense to store values that are already computed.
Some links: