You need to associate each search engine with a counter of how many times it was used. To do so, you'll need to keep the collection in memory and not create it each time.
First, create a class to represent your data:
class SearchEngine
{
public SearchEngine(string url, int counter)
{
Url = url;
Counter = counter;
}
public string Url { get; set; }
public int Counter { get; set; }
}
Second, create a collection of your engines as a private field somewhere:
private Random _random = new Random();
private IEnumerable<SearchEngine> _engines = new[]
{
new SearchEngine("www.google.com", 0),
new SearchEngine("www.bing.com", 0),
new SearchEngine("www.yahoo.com", 0)
};
And the method to get a random search engine should be like this:
private string GetRandomSearchEngine()
{
var searchEngine = _engines
// randomize the collection
.OrderBy(x => _random.Next())
// skip items with invalid counter
.SkipWhile(t => t.Counter >= 100)
.First();
// update the counter
searchEngine.Counter++;
return searchEngine.Url;
}
EDIT
As @Matt Burland suggests using _random.Next()
is a better approach to randomizing the collection.
He also raises another valid point: what happens when all the counters reach 100?
In such case, the code above will throw an exception (namely, the First()
method). Assuming you don't want that you can use FirstOrDefault()
and check for null
. If the returned item is null
then all counters have reached 100.
private bool TryGetRandomSearchEngine(out string url)
{
var searchEngine = _engines
// randomize the collection
.OrderBy(x => _random.Next())
// skip items with invalid counter
.SkipWhile(t => t.Counter >= 100)
.FirstOrDefault();
if(searchEngine != null)
{
// update the counter
searchEngine.Counter++;
url = searchEngine.Url;
return true;
}
url = String.Empty;
return false;
}
And somewhere in your code you can use the method above like this:
string searchEngineUrl;
while(TryGetRandomSearchEngine(out searchEngineUrl))
{
PerformSearch(searchEngineUrl, searchTerms);
}