C# Comparing data with database by using array - c#

My database contains 2 records. So, I retrieve these 2 records and store in array. Let's say my database have start point, destination, terminal and departure time. If user trying to add same start point, same destination, same terminal and same departure time, it will show error message. But if user trying to add same start point, same destination, same terminal but DIFFERENT departure time. It suppose to allow user add, but I having problem with user not allow to add.
Example:
These record are in my database
Record 1 : Terminal = 1 , From = US , To = UK, Time = 10.00
Record 2 : Terminal = 1 , From = US , To = AUS , Time = 2.00
When user want to add new record
User wish to add: Terminal = 1, From = US, To = AUS, Time = 10.00
It's tell me record exist because the time 10.00 exist in other record which is in different destination. Anyone can help?
if (ow_terminal.Any(s => ddlterminal.SelectedValue.Contains(s))
&& ow_depart.Any(s => ddlDeparture.SelectedValue.Contains(s))
&& ow_origin.Any(s => ddlOrigin.SelectedValue.Contains(s))
&& ow_destination.Any(s => ddlDestination.SelectedValue.Contains(s)))
{
lblMessage.Text = "Record exist";
}
else
{
lblMessage.Text = "No record exist"
}

The problem is with your Linq statement.
Think logically about what it is actually saying:
if(terminal_array.Any(s => new_terminal_record.Contains(s)))
So if ANY of the values in your terminal_array matches the new terminal record that the user entered then this statement is true, and your code will then evaluate the next line
if(depart_array.Any(s => new_depart_record.Contains(s)))
And it will do the same thing, if ANY of the values in your depart array matches the new departure record that the user entered then this statement is also true.
What you most likely want to do is to store the records in an array of whatever your record type is and do the Linq statement over each record in that array, something along the lines of:
if(records_array.Any(s => new_record.terminal.Equals(s.terminal) &&
new_record.depart.Equals(s.depart) &&
new_record.origin.Equals(s.origin) &&
new_record.destination.Equals(s.destination)))
{
// Record Exists
}
else
{
// No Record Exists
}
For a more complete example, I have replicated your implementation and then included my implementation:
class Program
{
// Example of database records
struct _dbTypes
{
public string terminal;
public string depart;
public string origin;
public string destination;
};
static void Main(string[] args)
{
// First record
_dbTypes record1;
record1.terminal = "1";
record1.depart = "10.00";
record1.origin = "US";
record1.destination = "UK";
// Second record
_dbTypes record2;
record2.terminal = "1";
record2.depart = "2.00";
record2.origin = "US";
record2.destination = "AUS";
// Your implementation has each of the records internals
// separated into their own array
List<String> terminals = new List<string>();
List<String> departs = new List<string>();
List<String> origins = new List<string>();
List<String> destination = new List<string>();
terminals.Add(record1.terminal);
terminals.Add(record2.terminal);
departs.Add(record1.depart);
departs.Add(record2.depart);
origins.Add(record1.origin);
origins.Add(record2.origin);
destination.Add(record1.destination);
destination.Add(record2.destination);
// The NEW record that the user has entered
_dbTypes record3;
record3.terminal = "1";
record3.depart = "10.00";
record3.origin = "US";
record3.destination = "AUS";
// Example of your implementation
if (terminals.Any(s => record3.terminal.Contains(s)) &&
departs.Any(s => record3.depart.Contains(s)) &&
origins.Any(s => record3.origin.Contains(s)) &&
destination.Any(s => record3.destination.Contains(s)))
{
// Will fall into here
Console.WriteLine("Record exists");
}
else
{
Console.WriteLine("No record exists");
}
// What you should probably be doing...
//
// Array of your record type
List<_dbTypes> dataBaseEntries = new List<_dbTypes>();
//
// Add the first two records as a whole record, not separated out
dataBaseEntries.Add(record1);
dataBaseEntries.Add(record2);
// Now you want to do the Linq statement over the record
// AND'ing each .Equals on the current records internal objects
if (dataBaseEntries.Any(s => record3.terminal.Equals(s.terminal) &&
record3.depart.Equals(s.depart) &&
record3.origin.Equals(s.origin) &&
record3.destination.Equals(s.destination)))
{
Console.WriteLine("Record exists");
}
else
{
Console.WriteLine("No record exists");
dataBaseEntries.Add(record3);
}
}
}

From what I can tell, you seem to be storing the information for each record in separate arrays, one each for terminal, depart, origin, and destination. This is a bit problematic since there isn't a concrete way of determining that the information belongs to the same record UNLESS for some reason, the information are ordered in the array per record:
example:
ow_terminal[0] = 1
ow_depart[0] = "US"
ow_origin[0] = "UK"
ow_destination[0] = 10.00
If this is the case, then you have to change your if statement logic. I don't think LINQ can help in this case, but you can try:
bool exists = false;
for(int i = 0; i < ow_terminal.Count; i++)
{
if(ddlterminal.SelectedValue.Contains(ow_terminal[i])
&& ddlDeparture.SelectedValue.Contains(ow_depart[i])
&& ddlOrigin.SelectedValue.Contains(ow_origin[i])
&& ddlDestination.SelectedValue.Contains(ow_destination[i]))
{
exists = true;
break;
}
}
if(exists) lblMessage.Text = "Record exist";
else lblMessage.Text = "No record exist";
The code checks the values of each array in the same position for equality. Again, this would only work if the items on all of the arrays are arranged per record. ALSO, you may want to change the equality check since Contains may not be best fit for your purpose ("US" is contained in "RUSSIA", for example.)
HOWEVER, managing four arrays and making sure that they are ordered correctly all the time is very fragile. What you want to do is to create just one array (or list) of objects that correspond to your record with corresponding properties:
public class FlightRecord
{
public int Terminal {get;set;}
public string From {get;set;}
public string To {get;set;}
public decimal Time {get;set;} // How are you storing time?
}
Create an array of FlightRecords from your database records and then you can do your logic like you wanted with a few minor changes:
if (ow_flightrecords.Any(s => ddlterminal.SelectedValue.Contains(s.Terminal.ToString()
&& ddlDeparture.SelectedValue.Contains(s.Time.ToString())
&& ddlOrigin.SelectedValue.Contains(s.From)
&& ddlDestination.SelectedValue.Contains(s.To)))
{
lblMessage.Text = "Record exist";
}
else
{
lblMessage.Text = "No record exist"
}
This one is more robust and you can use LINQ easily. Again, change how you do the comparisons since Contains may not be as good a fit for your purpose as you think it is.
And as Synchro noted, it's probably a good idea to do the check on the database directly via a stored procedure before you do the actual INSERT into the database. It will be much faster this way.

Related

If it possible accelerate From-Where-Select method?

I have two var of code:
first:
struct pair_fiodat {string fio; string dat;}
List<pair_fiodat> list_fiodat = new List<pair_fiodat>();
// list filled 200.000 records, omitted.
foreach(string fname in XML_files)
{
// get FullName and Birthday from file. Omitted.
var usersLookUp = list_fiodat.ToLookup(u => u.fio, u => u.dat); // create map
var dates = usersLookUp[FullName];
if (dates.Count() > 0)
{
foreach (var dt in dates)
{
if (dt == BirthDate) return true;
}
}
}
and second:
struct pair_fiodat {string fio; string dat;}
List<pair_fiodat> list_fiodat = new List<pair_fiodat>();
// list filled 200.000 records, omitted.
foreach(string fname in XML_files)
{
// get FullName and Birthday from file. Omitted.
var members = from s in list_fiodat where s.fio == FullName & s.dat == Birthdate select s;
if (members.Count() > 0 return true;
}
They make the same job - searching user by name and birthday.
The first one work very quick.
The second is very slowly (10x-50x)
Tell me please if it possible accelerate the second one?
I mean may be the list need in special preparing?
I tried sorting: list_fiodat_sorted = list_fiodat.OrderBy(x => x.fio).ToList();, but...
I skip your first test and change Count() to Any() (count iterate all list while any stop when there are an element)
public bool Test1(List<pair_fiodat> list_fiodat)
{
foreach (string fname in XML_files)
{
var members = from s in list_fiodat
where s.fio == fname & s.dat == BirthDate
select s;
if (members.Any())
return true;
}
return false;
}
If you want optimize something, you must leave comfortable things that offer the language to you because usually this things are not free, they have a cost.
For example, for is faster than foreach. Is a bit more ugly, you need two sentences to get the variable, but is faster. If you iterate a very big collection, each iteration sum.
LINQ is very powerfull and it's wonder work with it, but has a cost. If you change it for another "for", you save time.
public bool Test2(List<pair_fiodat> list_fiodat)
{
for (int i = 0; i < XML_files.Count; i++)
{
string fname = XML_files[i];
for (int j = 0; j < list_fiodat.Count; j++)
{
var s = list_fiodat[j];
if (s.fio == fname & s.dat == BirthDate)
{
return true;
}
}
}
return false;
}
With normal collections there aren't difference and usually you use foeach, LINQ... but in extreme cases, you must go to low level.
In your first test, ToLookup is the key. It takes a long time. Think about this: you are iterating all your list, creating and filling the map. It's bad in any case but think about the case in which the item you are looking for is at the start of the list: you only need a few iterations to found it but you spend time in each of the items of your list creating the map. Only in the worst case, the time is similar and always worse with the map creation due to the creation itself.
The map is interesting if you need, for example, all the items that match some condition, get a list instead found a ingle item. You spend time creating the map once, but you use the map many times and, in each time, you save time (map is "direct access" against the for that is "sequencial").

C# Help to validate table data before updating

I am working on a C# method that receives a json object containing the following values.
meetingid
o_agendaitem
o_legistarid
o_title
n_agendaitem
n_legistarid
n_title
The values with an "o" represent the record that comes from the database.
The values with an "n" represent the edited values from a web form.
I put all together to pass it to the C# method:
var data = JSON.stringify({
'meetingid': $scope.meetingId,
'o_agendaitem': o_xref.AgendaItem,
'o_legistarid': o_xref.LegistarID,
'o_title': o_xref.Title,
'n_agendaitem': n_xref.AgendaItem,
'n_legistarid': n_xref.LegistarID,
'n_title': n_xref.Title,
I am having trouble writing the logic in a clear and simple way.
For example, lets say I have the data below:
44841 1 62704 Title#1
44841 2 62218 Title#2
44841 3 62663 Title#3
44841 4 62679 Title#4
44841 5 62709 Title#5
The user edits the values, and changes the 1 for a 6, then the data would change to:
44841 2 62218 Title#2
44841 3 62663 Title#3
44841 4 62679 Title#4
44841 5 62709 Title#5
44841 6 62704 Title#6
Meeting Id and Agenda Item are a Composite Key.
I use the "o" agenda item value and meeting id, to find that record, and if exists, delete it, and then create a new entry with the "n" values.
But I need to check that the meeting id + the "n" agenda item don't exist already too.
Example:
44841 1 62704 Title#1
44841 2 62218 Title#2 < I edit this row, I want to change the 2 for a 6, but I made a mistake and instead entered a 5, then based on my current logic, I would be deleting a record I did not mean to delete. How can I add a new check to make sure that the user is made aware of this error?
44841 3 62663 Title#3
44841 4 62679 Title#4
44841 5 62709 Title#5
This is my attempt to accomplish so far (I added notes in the parts I am not sure if I am doing it right or not):
public ActionResult UpdateXRefItem(Parameters data)
{
bool status = false;
string message = "";
using (Entities entities = new Entities())
{
//use the "o" value to find the record
var oldRec = entities.XRef_WIP.Find(data.meetingId, data.o_agendaItem);
if (oldRec != null) {
//I am not sure if I should remove the record here, or better do a few more checks.
//entities.XRef_WIP.Remove(oldRec);
//use the "n" value combined with the meeting id to see if already exists
var newVal = entities.XRef_WIP.Find(data.meetingId, data.n_agendaItem);
//if the value from the form already exists, return a message to the user
if (newVal != null)
{
status = false;
message = "This Agenda Item already exists for this Cross-Reference List. Please verfy your data and try again.";
}
else{
//after removing the "old" record, and check that the combination of meeting id + agenda item
//do not exist alreay, then create a new table entry.
//I cannot update agenda item because it is part of the composite key.
//entities.XRef_WIP.Add(new XRefWIP
//{
// MeetingID = data.meetingId,
// AgendaItem = data.n_agendaItem,
// LegistarID = data.n_legistarId,
// Title = data.n_title
//});
//status = true;
//message = "Cross-Reference record has been succssfully updated.";
//entities.SaveChanges();
}
}
}
return new JsonResult { Data = new { status = status, message = message } };
}
I hope this makes sens and someone is willing to offer a hand to complete the logic. I think I am close, but I am having trouble putting my ideas together.
Thank you,
Erasmo
See if the solution works, the idea being that you check if the record you want to add exists and if it does you stop the user from proceeding.
public ActionResult UpdateXRefItem(Parameters data)
{
using (Entities entities = new Entities())
{
// First check if the item you are trying to add exists
var currentRec = entities.XRef_WIP.Find(data.meetingId, data.n_agendaItem);
// Stop the user from continueing with the transaction
if (currentRec != null)
return new JsonResult { Data = new { status = false, message = "Record already exists." } };
// Use the "o" value to find the record
var oldRec = entities.XRef_WIP.Find(data.meetingId, data.o_agendaItem);
// If it exists then delete it
if (oldRec != null) {
entities.XRef_WIP.Remove(oldRec);
// Add new record
entities.XRef_WIP.Add(new XRefWIP()
{
MeetingID = data.meetingId,
AgendaItem = data.n_agendaItem,
LegistarID = data.n_legistarId,
Title = data.n_title
});
// Return a new result
return new JsonResult { Data = new { status = true, message = "Success!" } };
}

LINQ query continues to return null after 1st successful call

I have an upload function in my ASP.NET MVC web application which allows a user to upload a document. The system then uses various OCR APIs to read data from the uploaded document, this data is then saved in the "SecondarySchoolSurvey" table in the database. I have a LINQ query in the upload code which finds a row in the database "SecondarySchoolSurvey" table that matches the Id passed in. Various fields in this row are then updated and saved back into the database.
Now this upload function works fine first time. Although if I try to use the upload function again (without restarting the IIS server) then it throws the following error Object reference not set to an instance of an object.
After setting various break points I noticed that the LINQ query: var s1 = db.SecondarySchoolSurveys.FirstOrDefault(s => s.Id == id); returns null the 2nd time it is called i.e. it does not find the record which matches the Id passed in, even though it exists in the database.
So for now, I need to reset the web app IIS server after every time I want to test the upload function. Otherwise this LINQ query with return null the 2nd time I try upload a document. Has anybody seen anything like this before? I'm not sure how useful it will be providing code but here is one of the class, the one which contains the LINQ query:
public class SurveyCheckboxAnswers
{
private RDSContext db = new RDSContext();
//Adds Question 2 answer
public void AddQ2Answer(SurveyCheckboxCollections checkboxes, int id)
{
//find Survey record in db which matches id in order to update with checkbox data
var s1 = db.SecondarySchoolSurveys.FirstOrDefault(s => s.Id == id);
CheckboxData q2Male = checkboxes.SecondarySchoolCheckboxes["Q2Male"];
CheckboxData q2Female = checkboxes.SecondarySchoolCheckboxes["Q2Female"];
CheckboxData q2Other = checkboxes.SecondarySchoolCheckboxes["Q2Other"];
CheckboxData q2DontWantToSay = checkboxes.SecondarySchoolCheckboxes["Q2DontWantToSay"];
//numbers of checkboxes marked for validation
int checkboxValidaiton = 0;
//update SecondarySchoolSurvey checkbox answers in database with IsChecked values from checkbox dictionary
if (q2Male.IsChecked)
{
s1.Q2 = Gender.Male;
checkboxValidaiton++;
}
if (q2Female.IsChecked)
{
s1.Q2 = Gender.Female;
checkboxValidaiton++;
}
if (q2Other.IsChecked)
{
s1.Q2 = Gender.Other;
checkboxValidaiton++;
}
if (q2DontWantToSay.IsChecked)
{
s1.Q2 = Gender.None;
checkboxValidaiton++;
}
//validate only 1 checkbox has been marked
if(checkboxValidaiton == 0)
{
s1.Flag = true;
s1.FlagContent += "| Question2: no checkboxes marked. ";
}
else if (checkboxValidaiton > 1)
{
s1.Flag = true;
s1.FlagContent += "| Question2: more than 1 checkboxes marked. ";
}
db.SaveChanges();
}
//Adds Question 6 answer
public void AddQ6Answer(SurveyCheckboxCollections checkboxes, int id)
{
//find Survey record in db which matches id in order to update with checkbox data
var s1 = db.SecondarySchoolSurveys.FirstOrDefault(s => s.Id == id);
CheckboxData q6Higher = checkboxes.SecondarySchoolCheckboxes["Q6Higher"];
CheckboxData q6Ordinary = checkboxes.SecondarySchoolCheckboxes["Q6Ordinary"];
CheckboxData q6Other = checkboxes.SecondarySchoolCheckboxes["Q6Other"];
//numbers of checkboxes marked for validation
int checkboxValidaiton = 0;
if (q6Higher.IsChecked)
{
s1.Q6a = MathLevel.Higher;
checkboxValidaiton++;
}
if (q6Ordinary.IsChecked)
{
s1.Q6a = MathLevel.Ordinary;
checkboxValidaiton++;
}
if (q6Other.IsChecked)
{
s1.Q6a = MathLevel.Other;
checkboxValidaiton++;
}
//validate only 1 checkbox has been marked
if (checkboxValidaiton == 0)
{
s1.Flag = true;
s1.FlagContent += "| Question6: no checkboxes marked. ";
}
else if (checkboxValidaiton > 1)
{
s1.Flag = true;
s1.FlagContent += "| Question6: more than 1 checkboxes marked. ";
}
db.SaveChanges();
}
//Adds Question 7 answer
public void AddQ7Answer(SurveyCheckboxCollections checkboxes, int id)
{
//find Survey record in db which matches id in order to update with checkbox data
var s1 = db.SecondarySchoolSurveys.FirstOrDefault(s => s.Id == id);
CheckboxData q7Physics = checkboxes.SecondarySchoolCheckboxes["Q7Physics"];
CheckboxData q7Biology = checkboxes.SecondarySchoolCheckboxes["Q7Biology"];
CheckboxData q7Chemistry = checkboxes.SecondarySchoolCheckboxes["Q7Chemistry"];
CheckboxData q7Science = checkboxes.SecondarySchoolCheckboxes["Q7Science"];
CheckboxData q7None = checkboxes.SecondarySchoolCheckboxes["Q7None"];
//numbers of checkboxes marked for validation
int checkboxValidaiton = 0;
if (q7Physics.IsChecked)
{
s1.Q7 = "Physics";
checkboxValidaiton++;
}
if (q7Biology.IsChecked)
{
s1.Q7 += "Biology";
checkboxValidaiton++;
}
if (q7Chemistry.IsChecked)
{
s1.Q7 += "Chemistry";
checkboxValidaiton++;
}
if (q7Science.IsChecked)
{
s1.Q7 += "Science Junior";
checkboxValidaiton++;
}
if (q7None.IsChecked)
{
s1.Q7 += "None";
checkboxValidaiton++;
}
//validate only 1 checkbox has been marked
if (checkboxValidaiton == 0)
{
s1.Flag = true;
s1.FlagContent += "| Question7: no checkboxes marked. ";
}
db.SaveChanges();
}
...
...
...
}
Your problem here most likely lies in the fact you are using a private variable for the db context. The appropriate way to open/close the connection to your db using a context is to use a using statement like so:
using(var db = new RDSContext())
{
//...Do work here with your context
}
Per MSDN
The lifetime of the context begins when the instance is created and ends when the instance is either disposed or garbage-collected. Use using if you want all the resources that the context controls to be disposed at the end of the block. When you use using, the compiler automatically creates a try/finally block and calls dispose in the finally block.
Since your query is running but is returning null, your db context is likely valid. That means the issue is likely the query itself. I suspect that on subsequent runs, you are passing in a different id that has no record in your database. Asking the db for the first record, if any, that matches the supplied id therefor returns null. Use a breakpoint to inspect both the provided id and the generated sql. Check in your db that you have a row for the id.
On another note, I would suggest that you use the method First or Single instead of FisrtOrDefualt if you expect the query to always return a row. This will throw an error if there are no matching rows, which guarantees that you have a not-null result returned if no error is thrown. The advantage is that after the method you now know that there was a matching row, whereas otherwise you may have to include a null check.
There is a great table on these operators here

How to update data in database using Entity Framework

I want to update data in a database using values from datagridview but I have not succeeded. My aim is to search through my datagrid view and if my product name exist in gridview, then I update the quantity.
if (bunifuDataGridView1.Rows.Count > 0)
{
foreach (DataGridViewRow row in bunifuDataGridView1.Rows)
{
if (Convert.ToString(row.Cells[2].Value) == bunifuTextBox11.Text)
{
row.Cells[5].Value = Convert.ToString(Convert.ToInt32(bunifuTextBox10.Text) + Convert.ToInt32(row.Cells[5].Value));
found = true;
obj5.ProductName = Convert.ToString(row.Cells[2].Value);
obj5.CostPricePerProduct = Convert.ToInt32(row.Cells[3].Value);
obj5.SellingPricePerProduct = Convert.ToInt32(row.Cells[4].Value);
obj5.Quantity = Convert.ToInt32(row.Cells[5].Value);
obj5.ExpiryDate = Convert.ToString(row.Cells[6].Value);
obj5.ProductNumber = Convert.ToInt32(obj2.ProductNumber);
obj5.Quantity = Convert.ToInt32(row.Cells[5].Value);
context.Entry.state = Entrystate.modified;
context.SaveChanges();
inboundgoods();
refreshcustomergrid();
}
}
if (!found)
{
inboundgoods();
}
}
else
{
inboundgoods();
}
I wish for my code to be able to search through datagridview for product name, and if there is a match, it should update that record by incrementing the stock quantity and save in stock database.
This is hard to debug without having the full app in front of us, but we can recommend some code changes that will assist with debugging:
if (bunifuDataGridView1.Rows.Count > 0)
{
foreach (DataGridViewRow row in bunifuDataGridView1.Rows)
{
// Compare the Product on each row, add a watch to this value to assist debugging
var product = Convert.ToString(row.Cells[2].Value);
if (product == bunifuTextBox11.Text) // consider rename bunfuTextBox11 to something meaningful, like 'ProductNameTextBox'
{
row.Cells[5].Value = Convert.ToString(Convert.ToInt32(bunifuTextBox10.Text) + Convert.ToInt32(row.Cells[5].Value)); // consider rename bunifuTextBox10 to something more meaningful like 'ProductQuantityTextBox'
found = true;
obj5.ProductName = Convert.ToString(row.Cells[2].Value);
obj5.CostPricePerProduct = Convert.ToInt32(row.Cells[3].Value);
obj5.SellingPricePerProduct = Convert.ToInt32(row.Cells[4].Value);
obj5.Quantity= Convert.ToInt32(row.Cells[5].Value);
obj5.ExpiraryDate = Convert.ToString(row.Cells[6].Value);
obj5.ProductNumber = Convert.ToInt32(obj2.ProductNumber);
obj5.Quantity = Convert.ToInt32(row.Cells[5].Value);
//context.Entry.state=Entrystate.modified;
// If your context has automatic change tracking enabled, this following line is not necessary
// But you need to make sure you are setting the State on the correct object tracker instance by passing it in to the Entry method.
var dbEntry = g.Entry(obj5);
if (dbEntry.State == EntryState.Detached)
dbEntry.State = EntryState.Added;
else
dbEntry.State = EntryState.Modified;
context.SaveChanges();
inboundgoods();
refreshcustomergrid();
}
}
if (!found)
{
inboundgoods();
}
}
else
{
inboundgoods();
}
If you are not getting to the found = true; line of code during debugging then review your comparison logic, look for spelling and whitespace issues, you may want to change the comparison to something like this if your inputs or stored data might have blank spaces or inconsistent letter casing.
if (product.Trim().Equals(bunifuTextBox11.Text.Trim(), StringComparison.OrdinalIgnoreCase))
Take the time to use meaningful names for your data entry field controls, it will make you code easier to read and understand, especially when you post code examples to forums like SO!

C# Updating Data Issue

I am currently using one button for inserting/updating content within a table. It then takes the uploaded CSV and inserts or updates it into a data table depending on whether the row exists or not.
Here is the code fired after the button's OnClick:
if (ExcelDDL.SelectedValue == "Time Points" && fileName == "TimePoints.csv")
{
var GetTPoints = (SEPTA_DS.TimePointsTBLDataTable)tpta.GetDataByCategory(CategoryDDL.SelectedItem.ToString());
//Loop through each row and insert into database
int i = 0;
foreach (DataRow row in TempRouteDataTable.Rows)
{
//Gather column headers
var category = Convert.ToString(CategoryDDL.SelectedItem);
var agency = Convert.ToString(row["Agency"]);
if (agency == null || agency == "")
{
//If row is empty skip it entirely
goto skipped;
}
var route = Convert.ToString(row["Route"]);
var GetRShortName = (SEPTA_DS.RoutesTBLDataTable)rta.GetDataByRouteID(route);
var newRoute = "";
if (GetRShortName.Rows.Count > 0)
{
newRoute = Convert.ToString(GetRShortName.Rows[0]["route_short_name"]);
}
var direction = Convert.ToString(row["Direction"]);
var serviceKey = Convert.ToString(row["Service Key"]);
var language = Convert.ToString(row["Language"]);
var stopID = Convert.ToString(row["Stop ID"]);
var stopName = Convert.ToString(row["Stop Name"]);
if (stopName.Contains("accessible"))
{
string[] noHTML = stopName.Split('>');
int insertH = Convert.ToInt32(hta.InsertHandicapRow(newRoute,noHTML[2]));
}
var sequence = Convert.ToString(row["Sequence"]);
var origID = -1;
if (GetTPoints.Rows.Count > 0)
{
origID = Convert.ToInt32(GetTPoints.Rows[i]["TPointsID"]);
var GetID = (SEPTA_DS.TimePointsTBLDataTable)tpta.GetDataByID(origID);
if (GetID.Rows.Count < 1)
{
origID = -1;
}
}
if (origID == -1)
{
int insertData = Convert.ToInt32(tpta.InsertTimePoints(category, agency, newRoute, direction, serviceKey, language, stopID, stopName, sequence));
}
else
{
int updateData = Convert.ToInt32(tpta.UpdateTimePoints(category, agency, newRoute, direction, serviceKey, language, stopID, stopName, sequence, origID));
}
skipped:
i++;
}
}
You can see how I check whether to insert or update around the bottom. I am using this method across other sections of this program and it works just fine. But in this case it is distorting my datatable immensely and I can't figure out why.
This is the bottom part of my table after inserting [no items currently within the database]:
This is the table after reuploading the CSV with data already existing within the table:
I am also getting this error when updating There is no row at position 2230.
What is going wrong in the code to cause this huge shift? I am just checking to see if the ID exists and if it does update rather than insert.
Also the reason i am using goto is because there are blank rows in the document that need to be skipped.
Is your TPointsID column, a auto-generated number? If so, since you are skipping the empty row, some referential integrity problem might be occuring,because of empty data in the skipped rows in the database.
From the error : There is no row at position 2230 , it is also understood that, because of the skipping you might be trying to access some non existent row in the datatable.
Also, if possible consider using the ADO.NET DataAdapter which has got the CRUD operation capability. You can find more about it at : http://support.microsoft.com/kb/308507

Categories