2009-05-07 7 views
7

Kennt jemand eine gute Klasse in .ged DateienGedcom Reader für C#

Gedcom ist ein Dateiformat zu lesen, die verwendet wird, genealogische Informationen zu speichern.

Mein Ziel ist es, etwas zu schreiben, die mir eine ged-Datei importieren lassen würde und eine .dot-Datei für graphviz exportieren, so dass ich

durch eine visuelle Darstellung eines Stammbaum machen können, wenn Sie helfen können

+2

Typo: geologische statt genealogischen –

+5

@ Joel C. (Tags): GEDCOM ein genealogisches Dateiformat ist, nicht Geologie oder die Entfernung zu kennen. (Die Aussage "visuelle Darstellung eines Familienstammbaums" mag auch geholfen haben ...) – GalacticCowboy

Antwort

5

Heres mein bester Versuch so weit.

Es scheint zu funktionieren, was ich allerdings seine defiently nicht vollen Beweis müssen (dann wieder mein Stammbaum ist ziemlich groß und fügt hinzu, dass eine gewisse Komplexität)

lassen Sie es mich wissen, wenn Sie denken, dass ich etwas mehr machen könnte elequient

struct INDI 
     { 
      public string ID; 
      public string Name; 
      public string Sex; 
      public string BirthDay; 
      public bool Dead; 


     } 
     struct FAM 
     { 
      public string FamID; 
      public string type; 
      public string IndiID; 
     } 
     List<INDI> Individuals = new List<INDI>(); 
     List<FAM> Family = new List<FAM>(); 
     private void button1_Click(object sender, EventArgs e) 
     { 
      string path = @"C:\mostrecent.ged"; 
      ParseGedcom(path); 
     } 

     private void ParseGedcom(string path) 
     { 
      //Open path to GED file 
      StreamReader SR = new StreamReader(path); 

      //Read entire block and then plit on 0 @ for individuals and familys (no other info is needed for this instance) 
      string[] Holder = SR.ReadToEnd().Replace("0 @", "\u0646").Split('\u0646'); 

      //For each new cell in the holder array look for Individuals and familys 
      foreach (string Node in Holder) 
      { 

       //Sub Split the string on the returns to get a true block of info 
       string[] SubNode = Node.Replace("\r\n", "\r").Split('\r'); 
       //If a individual is found 
       if (SubNode[0].Contains("INDI")) 
       { 
        //Create new Structure 
        INDI I = new INDI(); 
        //Add the ID number and remove extra formating 
        I.ID = SubNode[0].Replace("@", "").Replace(" INDI", "").Trim(); 
        //Find the name remove extra formating for last name 
        I.Name = SubNode[FindIndexinArray(SubNode, "NAME")].Replace("1 NAME", "").Replace("/", "").Trim(); 
        //Find Sex and remove extra formating 
        I.Sex = SubNode[FindIndexinArray(SubNode, "SEX")].Replace("1 SEX ", "").Trim(); 

        //Deterine if there is a brithday -1 means no 
        if (FindIndexinArray(SubNode, "1 BIRT ") != -1) 
        { 
         // add birthday to Struct 
         I.BirthDay = SubNode[FindIndexinArray(SubNode, "1 BIRT ") + 1].Replace("2 DATE ", "").Trim(); 
        } 

        // deterimin if there is a death tag will return -1 if not found 
        if (FindIndexinArray(SubNode, "1 DEAT ") != -1) 
        { 
         //convert Y or N to true or false (defaults to False so no need to change unless Y is found. 
         if (SubNode[FindIndexinArray(SubNode, "1 DEAT ")].Replace("1 DEAT ", "").Trim() == "Y") 
         { 
          //set death 
          I.Dead = true; 
         } 
        } 
        //add the Struct to the list for later use 
        Individuals.Add(I); 
       } 

       // Start Family section 
       else if (SubNode[0].Contains("FAM")) 
       { 
        //grab Fam id from node early on to keep from doing it over and over 
        string FamID = SubNode[0].Replace("@ FAM", ""); 

        // Multiple children can exist for each family so this section had to be a bit more dynaimic 

        // Look at each line of node 
        foreach (string Line in SubNode) 
        { 
         // If node is HUSB 
         if (Line.Contains("1 HUSB ")) 
         { 

          FAM F = new FAM(); 
          F.FamID = FamID; 
          F.type = "PAR"; 
          F.IndiID = Line.Replace("1 HUSB ", "").Replace("@","").Trim(); 
          Family.Add(F); 
         } 
          //If node for Wife 
         else if (Line.Contains("1 WIFE ")) 
         { 
          FAM F = new FAM(); 
          F.FamID = FamID; 
          F.type = "PAR"; 
          F.IndiID = Line.Replace("1 WIFE ", "").Replace("@", "").Trim(); 
          Family.Add(F); 
         } 
          //if node for multi children 
         else if (Line.Contains("1 CHIL ")) 
         { 
          FAM F = new FAM(); 
          F.FamID = FamID; 
          F.type = "CHIL"; 
          F.IndiID = Line.Replace("1 CHIL ", "").Replace("@", ""); 
          Family.Add(F); 
         } 
        } 
       } 
      } 
     } 

     private int FindIndexinArray(string[] Arr, string search) 
     { 
      int Val = -1; 
      for (int i = 0; i < Arr.Length; i++) 
      { 
       if (Arr[i].Contains(search)) 
       { 
        Val = i; 
       } 
      } 
      return Val; 
     } 
1

Ich wäre ziemlich überrascht, wenn es einen C# -Leser für dieses Format im Internet gibt, da es ein ziemlich spezialisiertes Format ist. Auf der Oberseite scheint das Format ziemlich einfach zu lesen, wenn Sie Ihren eigenen Leser erstellen müssen. Ich würde vorschlagen, diesen Weg einzuschlagen und zu SO zurückzukehren, wenn Sie spezifische Fragen zur Implementierung haben. Werfen Sie einen Blick auf die System.IO.StreamReader Klasse; Es ist trivial, in einer Datei Zeile für Zeile zu lesen, und das Parsen der einzelnen Zeilen sollte ebenfalls einfach sein.

Viel Glück!

+0

Ich weiß, dass das wahrscheinlich passieren wird. Ich möchte das möglichst vermeiden (das Rad muss nicht neu erfunden werden). – Crash893

+0

Ich denke, ich habe vielleicht eine Idee, wie ich das machen will - jedes Individuum ist abgegrenzt. dann wird jede Familie mit einem Zeiger auf die beteiligten Personen begrenzt. Ich denke, wenn nur gelesen, dass die Informationen in Ordnung gut sein. Ich wünschte, sie würden xml wie der Rest der zivilisierten Formate gehen. – Crash893

4

Es gibt eine sehr schöne bei Codeplex: FamilyShow (ein WPF-Showcase). Es importiert/exportiert GEDCOM 5.5 und es gibt Quelle.

+0

Familienshow ist ziemlich cool. Ich arbeite an etwas, um zu helfen, alles ähnlich zu visualisieren – Crash893

+0

Ich habe ein paar Tage mit Familienshow jetzt verbracht. und um ehrlich zu sein, es saugt @ # $ @ $. Es ist sehr hübsch, versteh mich nicht falsch, aber es ist auch sehr bugy (zumindest in xp) und nicht viele Dinge gut gut, von denen die wenigsten ist gedcom importieren – Crash893

4

Ich wäre eigentlich überrascht gewesen, wenn dort nicht mindestens die Anfänge von einem war. Ich fand Gedcom.NET (sourceforge) ziemlich leicht

+2

+1 für meine Kleingeistigkeit zu zeigen;) –

+0

I fand das auch. Dies könnte auch meine komplette Mangelerfahrung sein, aber die Klassenstruktur scheint ziemlich komplex zu sein. – Crash893

+1

Wäre hilfreich gewesen, das in Ihrer Frage zu erwähnen, und vielleicht, was Sie komplex finden. Es ist wahrscheinlich besser zu versuchen, um zu sehen, ob Sie das verstehen können (vielleicht kontaktieren Sie den Autor oder stellen Sie eine andere Frage hier), als eine einfachere Version neu zu erfinden, die nach und nach komplexer wird. –