tags:

views:

522

answers:

1

I am new to LINQ and am liking it so far, however I am trying to load in some forms by requesting a single record (student). If this doesn't exist I want't default values i.e. empty strings false bools...

so I used:

db = new DataClassesDataContext();        
student = db.ss_students.SingleOrDefault(p => p.student_id == studentID);
txtRegNumber.EditValue = student.car_reg_no;

This failed on the assignment of student.car_reg_no. I realised I seem to have mis-understood the SingleOrDefault method and it actually returns null for the student if it can't find a record. I for some reason was thinking it would return the default values for each of the fields such as student.car_reg_no. I think I am still thinkign in database mode.

This is not a problem I can do code like this:

db = new DataClassesDataContext();        
student = db.ss_students.SingleOrDefault(p => p.student_id == studentID);
if (student != null) 
{
        txtRegNumber.Text = student.car_reg_no;
        //assign more control values
}

And the defaults could either be assigned to the controls in an else or assigned direct on the form.

But is this the right way to do it or am I missing something?

EDIT Thanks for the posts so far I have started the approach suggested by Marc Gravell. I have now got a bit further.

I am now trying to save the data back to the database how would I know if I am updating or inserting a record. Should I be adding bools to record this myself or is their a built in way.

+5  A: 

SingleOrDefault returns the default value for the returned type. Which is

  • null for classes/interfaces/delegates
  • 0/false for value types
    • except for Nullable<T>, where it is null

For classes, you get null - this is mainly a way to check "did it exist?". Just create the actual default yourself... perhaps:

YourType x = query.SingleOrDefault() ?? new YourType();

This "null coalescing" approach only executes the right-hand-side (new ...) if the left-hand-side is null. Or more simply:

YourType x = query.SingleOrDefault();
if(x==null) { // use a default
    x = new YourType();
}
Marc Gravell
`FirstOrDefault` would be *slightly* cheaper if the ids can never be duplicates. `SingleOrDefault` will check that each time. (This isn't an issue with your answer, it's a comment in case the OP requested some unnecessary validation in the response.)
280Z28
Thanks started doing it this way have just added an edit to keep it in the same post for others. What happens when I want to save the data do I not need to know if it is (in sql terms) an insert or an update command.
PeteT
Since this is LINQ-to-SQL, worst case is that it has to read two rows from the database before throwing the exception...
Marc Gravell
@petebob796; interesting... you could use the `if` test and use `InsertOnSubmit` immediately, or you could check the primary key values later?
Marc Gravell
I think FirstOrDefault is a bit of a micro optimization for me. As I am learning I would prefer to get an error on more than one record in case I made a mistake on the lambada.
PeteT
@Marc if I use the InsertOnSubmit straight away is it ok to set the student values after? so I would assign student.car_reg_no a value after the InsertOnSubmit line. I think it is as the student object wouldn't be used until the actual submit.
PeteT
I believe so, yes. But it should be easy to find out (just check what values get saved...)
Marc Gravell