Reputation: 7
I am needing to check a list of numbers against a user inputted range, for instance, the user will input a range of 105323 to 106324. The list represents numbers the user knows are missing. So if the user inputs the range and the list contains 106100 and 106101, I am needing to output all the numbers in the range skipping or removing 106100 and 106101. I'm certain this is simple, but I'm just having trouble with the logic. Here is what I have so far
var startSeq = uxSeqStart.Text;
var startNum = Convert.ToInt32(startSeq);
var endSeq = uxSeqEnd.Text;
var endNum = Convert.ToInt32(endSeq);
for (var a = startNum; a <= endNum; a++)
{
foreach (int num in _MissingInt.ToList())
{
if (num + 1 == a) { _MissingInt.Remove(num); }
}
Console.WriteLine(a);//test output not a console app
}
}
I hope what I am asking makes sense. Please let me know if I am on the right path, any input is greatly appreciated
Upvotes: 1
Views: 362
Reputation: 37020
If I understand you correctly, you have a list of integers that should not be included in a range, and you get a range of integers from the user. Then you want to remove the "missing ints" from the range.
An easy way to generate a range of consecutive numbers is to use the System.Linq
method, Enumerable.Range()
, where you pass in a start number and a count of numbers to generate. We can use the start number that the user entered, but because they are entering an end number and not a count, we need to do a little math to determine the count:
// Generate a range of numbers based on the user input
var range = Enumerable.Range(startNum, endNum - startNum + 1);
Then you can use another System.Linq
extension method called Except()
on the range to remove the items in _MissingInt
list if they exist. Except
means "include all items from the original list except any that exist in another list":
// Remove any numbers in the _MissingInt from range if they exist
range = range.Except(_MissingInt);
Putting it all together, it would look like:
static void Main()
{
var _MissingInt = new List<int> { 106100, 106101 };
var startNum = 105323;
var endNum = 106101;
var range = Enumerable.Range(startNum, endNum - startNum + 1).Except(_MissingInt);
// Output the range with missing ints removed
Console.WriteLine("Modified Range:");
Console.WriteLine(string.Join(", ", range));
Console.Write("\nDone!\nPress any key to exit...");
Console.ReadKey();
}
Output
(Note that the last two numbers, which were in our _MissingInt
list are removed):
Upvotes: 2
Reputation: 1549
There are plenty of ways to do this.
Dmitry Bychenko solution is short and easy.
Since you are using integers only however, you can simply order your list of missing numbers and then finish the operation using a factor of N (Go through your sequence once) instead of N * Contains (For each number in the sequence, call Contains).
var startSeq = uxSeqStart.Text;
var startNum = Convert.ToInt32(startSeq);
var endSeq = uxSeqEnd.Text;
var endNum = Convert.ToInt32(endSeq);
Int[] missingInts = _MissingInt.ToList();
missingInts.sort();
foreach(int num in missingInts)
{
while(startNum <= endNum)
{
if (startNum == num)
{
startNum++;
break;
}
Console.WriteLine(startNum);
startNum++;
}
}
Upvotes: 0
Reputation: 186668
You can try using Linq in order to generate the collection (e.g. array):
HashSet<int> missing = new HashSet<int>() {
106100, 106101,
};
int start = 105323; // included
int stop = 106324; // included
var result = Enumerable
.Range(start, stop - start + 1)
.Where(item => !missing.Contains(item))
.ToArray();
Test
Console.Write(string.Join(" ", result));
Upvotes: 2