Avatar billede Henning3 Nybegynder
05. august 2010 - 13:41 Der er 12 kommentarer

Interne entity objekt referencer og MSSQL join

Hejsa
Jeg undrer mig ofte over denne problemstilling, som jeg kunne tænke mig at dele med jer andre.

Når jeg modelere min database som entity objekter i et C# class lib. og vil mappe til en 'sub' tabel, i koden så laver jeg en instance af den, hvis ikke den findes i forvejen og laver en join i min SQL.

Problemet er så, at hvis der ingen ID er i den tabel, som man joiner med, så vises dataene jo bare ik.

DB NavneTabel:
----------------------------------
ID | Navn.... osv.
----------------------------------
01 | Peter
02 | Hans
03 | Niels
----------------------------------

DB ByTabel:
----------------------------------
ID | NavneID | By.... osv.
----------------------------------
01 | 01 | Esbjerg
02 | 02 | Ribe
03 | null | Vejle
----------------------------------

Hvordan fikser jeg noget der, både på kode siden men også i SQL delen?

Mvh H.
Avatar billede softspot Forsker
05. august 2010 - 14:42 #1
Jeg er ikke sikker på at jeg forstår dit oplæg, men hvis du vil joine to tabeller hvor den refererede tabel (i dit tilfælde NavneTabel) ikke nødvendigvis indeholder en forekomst til primærtabellen, så kan du lave en left outer join i SQL, f.eks.

SELECT n.*, b.*
FROM ByTabel b
LEFT OUTER JOIN NavneTabel n ON n.ID = b.NavneID

I C# objektet kan du, alt efter hvad du vil opnå, oprette et tomt objekt til navne, hvor ID = 0 hvis navnet ikke eksisterer i forvejen i databasen. Du kan så i forbindelse med gem-operationen på by-objektets navn-objekt kontrollere om ID er nul og i så fald oprette det i databasen og ellers opdatere det, hvis ID er forskellig fra nul.

Alternativt kan du blot lade navn-objektet være null indtil det skal oprettes. Dette vil umiddelbart medføre flere check, da du skal sørge for at oprette det når der bliver brug for det. Dog vil det spare hukommelse at vente med at oprette det (det kunne jo være du slet ikke fik brug for det).

Jeg ved ikke om dette rent faktisk er det du tænker på, men det er i det mindste en gængs problemstilling :-)
Avatar billede Henning3 Nybegynder
05. august 2010 - 15:02 #2
det er præcist det jeg tænker på!

og LEFT OUTER JOIN virke.... :-D

I C# mener du noget ala eller mangler jeg noget????


public class NavneEntity
{
  private ID int = 0;
  private by_Feld ByEntity = null;

  .........

public ByEntity By_Feld
{
get
  {
  if (by_Feld == null)
  {
    by_Feld = new ByEntity();
  }
  return by_Feld ;
  }
set
  {
  by_Feld = value;
  }
}
.....
}
Avatar billede softspot Forsker
05. august 2010 - 15:28 #3
Hvis dette er dit objekt, så tror jeg du har byttet rundt på hvilken tabel der refererer hvilken i databasen. Det burde vel være navnetabel der refererede til bytabel med bytabellens id i navnetabel? Desuden er der lige et par syntaktise problemer med din C#-klasse (typen kommer før variabelnavnet). Bort set fra det, så er det nogenlunde det jeg mener, ja.

Dit tabeldesign skal nok se således ud:

DB NavneTabel:
----------------------------------
ID | Navn        | ById.... osv.
----------------------------------
01 | Peter      | 01
02 | Hans        | 02
03 | Niels      | null
----------------------------------

DB ByTabel:
----------------------------------
ID | By.... osv.
----------------------------------
01 | Esbjerg
02 | Ribe
03 | Vejle
----------------------------------
Avatar billede janus_007 Nybegynder
05. august 2010 - 17:07 #4
Hej Henning

Det lyder som om du laver en masse manuelt arbejde for at mappe, har du kigget på Linq To Sql , Linq to Entities?

Her får du alt det trivielle forærende mht. db-connections, mapping, joins, select, insert, update, delete mv. Det eneste det kræver er at du har styr på dine databaserelationer.
Avatar billede Henning3 Nybegynder
09. august 2010 - 10:49 #5
-> softspot; det er rigtigt, at jeg har lavet taste fejl i både mit DB tabeldesign eksempel her, samt i C# klassen. Felterne er naturligvis lavet i DB, som du har tilrettet det. Sorry.
Avatar billede Henning3 Nybegynder
09. august 2010 - 10:51 #6
-> janus_007; det er rigtigt. Jeg kender værktøjerne, men det er ikke i alle tilfælde at jeg syntes det er passende at bruge dem. Og så kan jeg godt lide selv at lave tingene, én gang imellem :-)
Avatar billede Henning3 Nybegynder
09. august 2010 - 10:56 #7
Har f.eks. entity factory klasser, hvor jeg laver mapningerne:

public class NavneFactory : IDomainObjectFactory<NavneEntity>
    {

        public Wine Construct(IDataRecord record)
        {
            if (record == null)
                throw new ArgumentNullException("record");

            NavneEntity domainObj = new NavneEntity();

            domainObj.ID = record["Navne.ID"] is DBNull ? 0 : Convert.ToInt32(record["Navne.ID"]);

domainObj.Navn = record["Navne.Navn"] is DBNull ? string.Empty : (string)(record["Navne.Navn"]);

...............................

// Kald til objekt reference!

domainObj.ByEntity.ByNavn = record["By.Navn"] is DBNull ? string.Empty : (string)record["By.Navn"];

return domainObj;
}
    }
Avatar billede Henning3 Nybegynder
09. august 2010 - 10:58 #8
-> softspot; du skriver det er nogenlunde sådan du ville lave det i C# klassen???????

kommer du med et svar, så smider jeg points til dig. Det skulle jo nok have været et MSSQL spørgsmål, men hva f...! :-)
Avatar billede janus_007 Nybegynder
09. august 2010 - 12:29 #9
Henning3, nåh ja jeg synes det er totalt tidsspilde at lave trivielle ting som andre alligevel kan lave 100 gange bedre end mig selv.

Men ud af nysgerrighed... Hvilke tilfælde synes du ikke det passer til?
Avatar billede Henning3 Nybegynder
11. august 2011 - 12:33 #10
beklager det sene svar...
Avatar billede Henning3 Nybegynder
11. august 2011 - 12:42 #11
ups... troede jeg kunne vælge at give points når jeg valgte Svar i radioknaplisten. Smid et svar janus007, så smider jeg points.
Avatar billede Henning3 Nybegynder
11. august 2011 - 12:43 #12
og softspot selvfølgelig.
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Kurser inden for grundlæggende programmering

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester