The idea is simply that the respawn timing is adjusted based on the existing number of enemies of that particular type, with the timer set from the time the LAST respawn happened.
This example is from BTL Finale.
The following code block MUST be placed in the script of a SINGLE, Unique CRE within the map itself. If you don't have such a CRE (like a boss, for example) you can use an invisible, invulnerable CRE for this. Why is that so, is because NumCreatureLT only measures the creatures sharing on the same map as the CRE. For very big maps, you may wish to use other triggers to check for the number.
// Timer Controllers Lead to Spawning
// Assassin Summoning
IF Global("Z#SeidaAssas","Z#0041",1)
Global("Z#SeidaAssasTSet","Z#0041",1)
NumCreatureLT("Z#Assas3",4)
GlobalTimerExpired("Z#SeidaAssasT3","Z#0041")
THEN
RESPONSE #100
SetGlobal("Z#SpawnAssas","Z#0041",1)
Continue()
END
IF Global("Z#SeidaAssas","Z#0041",1)
Global("Z#SeidaAssasTSet","Z#0041",1)
NumCreatureGT("Z#Assas3",3)
NumCreatureLT("Z#Assas3",6)
GlobalTimerExpired("Z#SeidaAssasT5","Z#0041")
THEN
RESPONSE #100
SetGlobal("Z#SpawnAssas","Z#0041",1)
Continue()
END
IF Global("Z#SeidaAssas","Z#0041",1)
Global("Z#SeidaAssasTSet","Z#0041",1)
NumCreatureGT("Z#Assas3",5)
NumCreatureLT("Z#Assas3",

GlobalTimerExpired("Z#SeidaAssasT7","Z#0041")
THEN
RESPONSE #100
SetGlobal("Z#SpawnAssas","Z#0041",1)
Continue()
END
There are 3 timers here - Z#SeidaAssasT3,5,7 corresponding respectively to 0-3 remaining assassins, 4-5 remaining assassins, 6-7 remaining assassins. Since 8 is the max number for this scenario there is no check for it.
=================
All of the rest of the following code is best placed in the BAF script of the ARE.
This first block causes the Assassin to spawn when the conditions in the CRE's AI Script are fulfilled.
// Spawning
IF Global("Z#SpawnAssas","Z#0041",1)
GlobalLT("Z#MeetingSeida","GLOBAL",5)
THEN
RESPONSE #50
SetGlobal("Z#SpawnAssas","Z#0041",0)
SetGlobal("Z#SeidaAssasTSet","Z#0041",0)
CreateCreatureOffScreen("Z#Assas3",0)
Continue()
END
I used "Z#SeidaAssasTSet" to trigger the resetting of the respawn timers. Looking back its not very necessary but it sure makes it a hell a lot neater. There's no real reason why you shouldn't just lump the RESPONSE portion of the below block to replace SetGlobal("Z#SeidaAssasTSet","Z#0041",0).
// Timers
IF Global("Z#SeidaAssas","Z#0041",1)
Global("Z#SeidaAssasTSet","Z#0041",0)
THEN
RESPONSE #100
SetGlobalTimer("Z#SeidaAssasT3","Z#0041",7)
SetGlobalTimer("Z#SeidaAssasT5","Z#0041",14)
SetGlobalTimer("Z#SeidaAssasT7","Z#0041",24)
SetGlobal("Z#SeidaAssasTSet","Z#0041",1)
Continue()
END
========
There's too many variations for this, like different conditions to check for different timers used to count, applying to different number of foes, randomising the number of enemies spawned at one time (in this example only one is spawned, for example), or starting the Timer not from the last respawn, but from the time that the number falls below 8, etc etc. None of it should be too difficult since you have this codeblock to refer to.