Increment count in c# - c#

I am trying to create a query. Here is the code
string wherequery = "";
int fromcode = Convert.ToInt32(CodeTextBox.Text);
int count = Convert.ToInt32(CountTextBox.Text);
for (int i = 0; i < count; i++)
wherequery += ("'" + (fromcode + i).ToString().PadLeft(8,'0') + "',");
wherequery = wherequery.TrimEnd(",");
I am using for loop to create a IN query. Is it possible via LINQ?
Output should be
'0000000087','0000000088','0000000089'
Second thing, I get the code from a textbox value like 0000000087. When I convert it into int using Convert.ToInt32, preceding 0s get disappeared.
Is it possible that 0s shouldn't get disappear since number of preceding 0s may vary?

No need for .PadLeft(8,'0') which causes unnecessary leading zeros.
Try following.
var whereQueryFormat = "Whre columnName IN ({0})";
var wherequery = string.Join
(",",
Enumerable.Range(1, count)
.Select(i => "'" + fromcode + i + "'")
);
wherequery = string.Format(whereQueryFormat, wherequery);

I am not quite sure if you can use LINQ at this point. Here is an example how I would solve this problem:
Dim whereQuery As String = ""
Dim operatorValues As New List(Of String)
Dim startingNumber As String = CodeTextBox.Text
Dim lengthOfNumber As Integer = startingNumber.Length
Dim count As Integer = Convert.ToInt32(CountTextBox.text)
For i As Integer = CInt(startingNumber) To CInt(startingNumber + count - 1)
operatorValues.Add(i.ToString.PadLeft(lengthOfNumber, "0"))
Next
whereQuery &= "IN ('" & Join(operatorValues.ToArray, "','") & "')"
Anyway: Why is your database-field a string and not a integer? Then you would not have a problem with the leading zeros.

If you want to remove the for operation, you could probably do it this way using LINQ, Enumerable.Range, and string.Join:
int fromcode = Convert.ToInt32(CodeTextBox.Text);
int count = Convert.ToInt32(CountTextBox.Text);
var words = from i in Enumerable.Range(fromcode, count)
select "'" + i.ToString().PadLeft(8, '0') + "'";
string wherequery = string.Join(",", words);

You will still have to use a loop for this. But the below code address your variable padded zeros issue.
var enteredValue = "00000088";//get this from the text box
int enteredCount = 10;//get this from the text box
string wherequery = "";
int fromCode = Convert.ToInt32(enteredValue);
string fromCodeStr = fromCode.ToString(CultureInfo.CurrentCulture);
string padZeros = enteredValue.Split(new[] {fromCodeStr}, StringSplitOptions.None)[0];
List<string> searchList = new List<string>();
for (int i = 1; i <= enteredCount; i++)
{
searchList.Add(padZeros + fromCode + i);
}
var searchString = string.Join(",", searchList);

If you want to use LINQ to get the IN clause you can use this:
var range = Enumerable.Range(0, count).Select(x =>
string.Format("'{0}'", x.ToString("0000000000")));
var inCluase = string.Format(" IN ({0})", string.Join(",", range));

Related

Instead of if statements use a loop?

Is there any way I could use a loop instead of writing out all of these if/else statements? I'm not sure if it is possible and I have looked online and haven't seen very many guides that would help me.
int numberOne = random.Next(id2) + 1;
int numberTwo = random.Next(id2) + 1;
int numberThree = random.Next(id2) + 1;
int numberFour = random.Next(id2) + 1;
int numberFive = random.Next(id2) + 1;
if (id1 == 1)
{
int total = numberOne;
string newmessage = "message";
return Json(newmessage);
}
else if(id1 == 2)
{
int total = numberOne + numberTwo;
string newmessage = "message";
return Json(newmessage);
}
else if (id1 == 3)
{
int total = numberOne + numberTwo + numberThree;
string newmessage = "message";
return Json(newmessage);
}
else if (id1 == 4)
{
int total = numberOne + numberTwo + numberThree + numberFour;
string newmessage = "message";
return Json(newmessage);
}
else if (id1 == 5)
{
int total = numberOne + numberTwo + numberThree + numberFive;
string newmessage = "message";
return Json(newmessage);
}
What you likely want to do is:
int total = Enumerable.Range(1, id1).Sum(z => random.Next(id2) + 1);
string newmessage = "message";
return Json(newmessage);
There is no need for an explicit loop (since Enumerable.Range will do the looping for you).
Since you probably need a loop and not using lambdas, you can go with something like this:
int total = 0;
for (int i = 0; i < id1; i++)
{
total += random.Next(id2) + 1;
}
return Json("message"); // I assume you want to return total here;
The reason this works is that if id1 is 1, you'd break out of the loop after doing 1 random.Next. If id2 is 2, then you'd run thru the first number and then add the 2nd number automatically. With this approach, you could support any number, not just up to 5.
I'd go with #mjwills solution, but here's an explanation of how you might do it in a step by step fashion:
The first thing I did was declare random, id1 and id2. I varied id1 during testing. When you post code, you should include this kind of thing, that way the folks help you don't have to reverse engineer what you are thinking:
var id1 = 5;
var id2 = 10;
var random = new Random();
Then, I realize that in each case, you have a chunk of the same code (the last two lines), so I extracted that duplicated code out and put it at the bottom of the loop (and I used NewtonSoft's JsonConvert class to convert things to JSON (which I'm assuming your Json function does) - I have that NuGetted into my test project):
string newMessage = "message";
return JsonConvert.SerializeObject(newMessage);
Finally, here's the loop you were asking about. I initialize total (I could put that initialization in the for loop, but it's clearer this way). Also note that the for loop is non-standard, it loops from 1 to N inclusive (generally for loops are 0 to N-1). This loop is between the initialization code and the final code:
var total = 0;
for (var i = 1; i <= id1; ++i)
{
total += (random.Next(id2) + 1);
}
What #mjwills code does is convert that into a single expression. The Enumerable.Range(1, id1) part generates a collection of consecutive integers starting at 1 and having id1 entries. Then he calls .Sum, passing it a lambda that represents a function to run on each item in the collection before it is summed. My loop basically does the same thing.
Altogether, it looks like this:
var id1 = 5;
var id2 = 10;
var random = new Random();
var total = 0;
for (var i = 1; i <= id1; ++i)
{
total += (random.Next(id2) + 1);
}
string newMessage = "message";
return JsonConvert.SerializeObject(newMessage);
try this, it also allows you init 5 numbers using any algoritm, not just the same
//var random=new Random();
//var id2=2;
//var id1=4;
var data = new int[]{
random.Next(id2) + 1,
random.Next(id2) + 1,
random.Next(id2) + 1,
random.Next(id2) + 1,
random.Next(id2) + 1
};
var total=0;
for ( var i = 0; i < id1; i++)
{
total+=data[i];
}
var newmessage = $"message#{id1.ToString()}, total {total.ToString()} ";
return Json(newmessage);

how to show number of digits on users's request?

for example: if a string value is "123456.7890" .
if user enters the length 6 and the other value 2 for the decimal place.
the output value should be like "123456.78"
if user enters the length 5 and the other value 3 for the decimal place.
the output value should be like "12345.789"
string s = "123456.7890";
string a = string.Format("{0, 2:F2}", s);
int index = a.IndexOf('.');
a = a.Substring(index, (a.Length-index));
One approach could be like this:
NOTE: If the string's length is less than the number of characters you're taking, code will throw an exception ArgumentOutOfRangeException
int LeftPlaces = 4;
int RightPlaces = 2;
String Input = "123456.7890";
String[] Splitted = Input.Split('.');
String StrLeft = Splitted[0].Substring(0, LeftPlaces);
String StrRight = Splitted[1].Substring(0, RightPlaces);
Console.WriteLine(StrLeft + "." + StrRight);
Output: 1234.78
The most crude and direct way would be:
var length = 5;
var decimalPlaces = 2;
var s = "123456.7890";
var data = s.Split('.');
var output1 = data[0].Substring(0, length);
var output2 = data[1].Substring(0, decimalPlaces);
var result = output1 + "." + output2;
If you want to do this without strings, you can do so.
public decimal TrimmedValue(decimal value,int iLength,int dLength)
{
var powers = Enumerable.Range(0,10).Select(x=> (decimal)(Math.Pow(10,x))).ToArray();
int iPart = (int)value;
decimal dPart = value - iPart;
var dActualLength = BitConverter.GetBytes(decimal.GetBits(value)[3])[2];
var iActualLength = (int)Math.Floor(Math.Log10(iPart) + 1);
if(dLength > dActualLength || iLength > iActualLength)
throw new ArgumentOutOfRangeException();
dPart = Math.Truncate(dPart*powers[dLength]);
iPart = (int)(iPart/powers[iActualLength - iLength]);
return iPart + (dPart/powers[dLength]);
}
Client Call
Console.WriteLine($"Number:123456.7890,iLength=5,dLength=3,Value = {TrimmedValue(123456.7890m,5,3)}");
Console.WriteLine($"Number:123456.7890,iLength=6,dLength=2,Value = {TrimmedValue(123456.7890m,6,2)}");
Console.WriteLine($"Number:123456.7890,iLength=2,dLength=4,Value = {TrimmedValue(123456.7890m,2,4)}");
Console.WriteLine($"Number:123456.7890,iLength=7,dLength=3,Value = {TrimmedValue(123456.7890m,7,3)}");
Output
Number:123456.7890,iLength=5,dLength=3,Value = 12345.789
Number:123456.7890,iLength=6,dLength=2,Value = 123456.78
Number:123456.7890,iLength=2,dLength=4,Value = 12.789
Last call would raise "ArgumentOutOfRangeException" Exception as the length is more than the actual value

Split string by length to Excel

I am currently sending and splitting long lines of data to Excel. Each split prints in a new row. I want to change this from splitting at a pipe symbol in the existing data to splitting at a character length of 85, but , there are chances that at character 85 it may split a word in two. How would I tell it to split further into the data if is going to split an actual word. I know if at 85 it should also find a space after. I'm curious on what to add.
// Add Description
string DescriptionSplit = srcAddOnPanel.Controls["txtProductDescAddOn" + AddRow].Text;
string[] descriptionParts = DescriptionSplit.Split('|');
int i;
for (i = 0; i <= descriptionParts.GetUpperBound(0); i++)
{
worksheet.Rows[currentRow].Insert(); //applies the description for the default bundle row
worksheet.Rows[currentRow].Font.Bold = false;
worksheet.Cells[currentRow, "E"].Value = rowIndent + descriptionParts[i].Trim();
currentRow++;
}
You could use this approach (Warning not fully tested)
int x = 85;
int y = 0;
int currentRow = 0;
// Loop until you have at least 85 char to grab
while (x + y < DescriptionSplit.Length)
{
// Find the first white space after the 85th char
while (x + y < DescriptionSplit.Length &&
!char.IsWhiteSpace(DescriptionSplit[x+y]))
x++;
// Grab the substring and pass it to Excel for the currentRow
InsertRowToExcel(DescriptionSplit.Substring(y, x), currentRow);
// Prepare variables for the next loop
currentRow++;
y = y + x + 1;
x = 85;
}
// Do not forget the last block
if(y < DescriptionSplit.Length)
InsertRowToExcel(DescriptionSplit.Substring(y), currentRow);
...
void InsertRowToExcel(string toInsert, int currentRow)
{
worksheet.Rows[currentRow].Insert();
worksheet.Rows[currentRow].Font.Bold = false;
worksheet.Cells[currentRow, "E"].Value = rowIndent + toInsert.Trim();
}
Here's a VBA version that seems to work. As suggested in my comment, it separates the string by spaces and then tests whether adding a word makes the length of the current line greater than the maximum (85). As is usual with these kinds of things getting the last word to populate correctly is hard.
If this works for you it should be simple enough to modify to C#. Let me know if that's not true:
Sub ParseRows()
Const ROW_LENGTH As Long = 85
Dim Text As String
Dim Words As Variant
Dim RowContent As String
Dim RowNum As Long
Dim i As Long
Text = ActiveCell.Text
Words = Split(Text, " ")
RowNum = 2
For i = LBound(Words) To UBound(Words)
If Len(RowContent & Words(i) & " ") > ROW_LENGTH Then
ActiveSheet.Range("A" & RowNum).Value = RowContent
RowNum = RowNum + 1
If i = UBound(Words) Then
RowContent = Words(i)
Else
RowContent = ""
End If
Else
RowContent = RowContent & Words(i) & " "
End If
Next i
If RowContent <> "" Then ActiveSheet.Range("A" & RowNum).Value = RowContent
End Sub

How to insert a space into a string, between every 4 characters? [duplicate]

This question already has answers here:
Add separator to string at every N characters?
(15 answers)
Closed 8 years ago.
The string displays value as:
123456789012
I need it like:
1234 5678 9012
There should be space between every 4 characters in this string. How do I do that?
displaynum_lbl.Text = Regex.Replace(printClass.mynumber.ToString(), ".{4}", "$0");
Assuming that it's fine to work from right-to-left, this should do the trick:
displaynum_lbl.Text = System.Text.RegularExpressions.Regex.Replace(printClass.mynumber.ToString(), ".{4}", "$0 ");
You can find that and a good deal more information in other StackOverflow answers, example: Add separator to string at every N characters?
String abc = "123456789012";
for (int i = 4; i <= abc.Length; i += 4)
{
abc = abc.Insert(i, " ");
i++;
}
You can do this in LINQ:
var s = "123456789012";
var list = Enumerable
.Range(0, s.Length/4)
.Select(i => s.Substring(i*4, 4))
.ToList();
var res = string.Join(" ", list);
Console.WriteLine(res);
Fiddle
public string InsertSpaces(string s)
{
char[] result = new char[s.Length + (s.Length / 4)];
for (int i = 0, target = 0; i < s.Length; i++)
{
result[target++] = s[i];
if (i & 3 == 3)
result[target++] = ' ';
}
return new string(result);
}

Substring with dynamic length

I need to get value of below string into 2 variables.
Input
6.3-full-day-care
Expected output:
var price=6.3; //The input is dynamic.Cannot get fixed length
var serviceKey="full-day-care";
How can I do that? Substring doesn't help here.
You can use String.Split and String.Substring methods like;
string s = "6.3-full-day-care";
int index = s.IndexOf('-'); //This gets index of first '-' character
var price = s.Substring(0, index);
var serviceKey = s.Substring(index + 1);
Console.WriteLine(price);
Console.WriteLine(serviceKey);
Output will be;
6.3
full-day-care
Here a DEMO.
you can do like:
var val = "6.3-full-day-care";
var index = val.IndexOf("-"); //first occuarance of -
var price =double.Parse(val[index]);
var serviceKey = val.Substring(index);
Just to give idea. It's beter naturally use double.TryParse(..) on price
double price = 0;
double.TryParse(val[index], out prince, System.Globalization.InvariantCulture);
This should work
var s = "6.3-full-day-care";
var index = s.IndexOf('-');
var price = s.Substring(0, index);
var serviceKey = s.Substring(index + 1);
If the price and the key are always separated with a '-':
string s = "6.3-full-day-care";
int separatorIdx = s.IndexOf( '-' ); // get idx of first '-'
// split original string
string price = s.Substring( 0, separatorIdx );
string serviceKey = s.Substring( separatorIdx+1, s.Length );
Use String.Split with a maximum count http://msdn.microsoft.com/en-us/library/c1bs0eda.aspx
string s = "6.3-full-day-care";
string[] parts = s.split(new char[]{'-'}, 1);
var price = parts[0];
var serviceKey = parts[1];

Categories