There is value is having a dynamic number of threads. It means that the system administrator does not need to pick a number and hope it works. Even if the sysadmin is very clever, there will often be either too many threads, wasting memory, or too few causing uneeded delays. Having a dynamic number of threads means that the number can follow load.
It would seem sensible that the number of threads should be able to grow quickly (but not too quickly) and that it should fall slowly as demand drops. This would mean that there are usually enough threads to handle requests.
It would be quite practical to manage the number of threads from user space. A program could monitor the thread usage from /proc/net/rpc/nfsd. It is not certain that there is enough precision in these numbers, but it could be enough. Certainly the program could tell every time that the last thread was used, and could use that to trigger the spawning of a new thread.
Choosing an appropriate rate of thread birth and death is an interesting question. It would be important to choose numbers that scaled appropriately with the performance of the machine. If the hardware regularly copes with a very high rate of requests, then increasing the thread count quickly is more appropriate than on a machine which isn't as fast.
It might be appropriate to aim for 90% thread usage, and to have one birth rate that applied when usage was above 90%, and another that applied when usage hit 100%.
Possibly it would be good to do some long-term load monitoring. We keep an idea of the max load, which decays very slowly, and allow thread usage to grow to that max quickly. Then we retard growth to a more reasonable rate, each time confirming that more are needed before adding new threads.
Thread reaping should probably have a target time period for stability. Say 5 minutes. If number of threads exceeds the apparent need (allowing for 10% overhead), we kill threads at a rate that means we will reach the target in the given time.
It would be good to prototype this with a simple script that monitored /proc/net/rpc/nfsd and adjusted thread count accordingly. If it turned out that kernel support was needed, that could be added later.