Exemple #1
0
        // =========================== Основные выборки и поиски ===============================

        public override XElement GetItemByIdBasic(string id, bool addinverse)
        {
            int cid = store.CodeEntity(id);

            object[] tri = (object[])store.GetRecord(cid);
            if (tri == null)
            {
                return(null);
            }
            object[] pair = ((object[])tri[1]).Cast <object[]>().FirstOrDefault(dup => (int)dup[0] == store.cod_rdftype);
            XElement xres = new XElement("record",
                                         new XAttribute("id", id), pair == null?null: new XAttribute("type", store.DecodeEntity((int)pair[1])),
                                         ((object[])tri[2]).Cast <object[]>().Select(dup =>
            {
                return(new XElement("field", new XAttribute("prop", store.DecodeEntity((int)dup[0])),
                                    ((string)dup[2] == ""?null: new XAttribute("{http://www.w3.org/XML/1998/namespace}lang", (string)dup[2])),
                                    (string)dup[1]));
            }),
                                         ((object[])tri[1]).Cast <object[]>().Where(dup => (int)dup[0] != store.cod_rdftype).Select(dup =>
            {
                return(new XElement("direct", new XAttribute("prop", store.DecodeEntity((int)dup[0])),
                                    new XElement("record", new XAttribute("id", store.DecodeEntity((int)dup[1])))));
            }),
                                         null);

            if (addinverse)
            {
                var inv = store.GetRefers(cid);
                xres.Add(inv.Cast <object[]>().Select(tr =>
                {
                    int c          = (int)tr[0];
                    object[] found = ((object[])tr[1]).Cast <object[]>().FirstOrDefault(dup => (int)dup[1] == cid);
                    return(new XElement("inverse", new XAttribute("prop", store.DecodeEntity((int)found[0])),
                                        new XElement("record", new XAttribute("id", store.DecodeEntity(c)))));
                }));
            }
            return(xres);
        }
        public TripleStoreProfile(TripleRecordStore store)
        {
            _store = store;
            // Вычисление "важных" кодов
            cod_rdftype = store.CodeEntity("http://www.w3.org/1999/02/22-rdf-syntax-ns#type"); // Зафиксирован? 0;
            cod_delete  = store.CodeEntity("http://fogid.net/o/delete");
            cod_name    = store.CodeEntity("http://fogid.net/o/name");
            CreateMap <object, RecordField>().ConstructUsing((triples, context) =>
            {
                if (!(triples is object[] dup))
                {
                    return(null);
                }
                return(new RecordField()
                {
                    Property = store.Decode((int)dup[0]),
                    Value = (string)dup[1]
                });
            });
            CreateMap <object, RecordProperty>().ConstructUsing((triples, context) =>
            {
                if (!(triples is object[] dup))
                {
                    return(null);
                }
                return(new RecordProperty()
                {
                    Property = store.DecodeEntity((int)dup[0]),
                    Value = new Record()
                    {
                        Id = store.DecodeEntity((int)dup[1])
                    }
                });
            });
            CreateMap <object, RecordInverseProperty>().ConstructUsing((source, context) =>
            {
                if (!(source is object[] triples))
                {
                    return(null);
                }
                int cid        = (int)triples[0];
                object[] found = ((object[])triples[1]).Cast <object[]>().FirstOrDefault(dup => (int)dup[1] == cid);
                return(new RecordInverseProperty()
                {
                    Property = store.DecodeEntity((int)found[0]),
                    Value = new Record()
                    {
                        Id = store.DecodeEntity((int)triples[0])
                    }
                });
            });

            CreateMap <object, Record>().ConstructUsing((source, context) =>
            {
                if (!(source is object[] triples))
                {
                    return(null);
                }
                if (context.Options.Items["Format"] is RecordFormat format)
                {
                    //todo use format recursive
                    return(new Record()
                    {
                        Id = store.DecodeEntity((int)triples[0]),
                        Type = GetRecordType(source),
                        Fields = context.Mapper.Map <RecordField[]>(((object[])triples[2])),
                        Directs = context.Mapper.Map <RecordProperty[]>((object[])triples[1])
                    });
                }

                return(new Record()
                {
                    Id = store.DecodeEntity((int)triples[0]),
                    Type = GetRecordType(source),
                    Fields = context.Mapper.Map <RecordField[]>((object[])triples[2]),
                    Directs = context.Mapper.Map <RecordProperty[]>((object[])triples[1])
                });
            });
            CreateMap <object, RecordWithInverses>().ConstructUsing((source, context) =>
            {
                if (!(source is object[] triples))
                {
                    return(null);
                }
                return(new RecordWithInverses()
                {
                    Id = store.DecodeEntity((int)triples[0]),
                    Type = GetRecordType(source),
                    Fields = context.Mapper.Map <RecordField[]>((object[])triples[2]),
                    Directs = context.Mapper.Map <RecordProperty[]>((object[])triples[1]),
                    Inverses =
                        context.Mapper.Map <IEnumerable <RecordInverseProperty> >(store.GetRefers((int)triples[0]))
                        ?.ToArray()
                });
            });

            CreateMap <Record, XElement>().ConvertUsing((record, context) =>
            {
                if (record == null)
                {
                    return(null);
                }
                XElement xres = new XElement("record",
                                             new XAttribute("id", record.Id), record.Type == null ? null : new XAttribute("type", record.Type),
                                             record.Fields?.Select(dup => new XElement("field", new XAttribute("prop", dup.Property), dup.Value)),
                                             record.Directs?.Select(dup => new XElement("direct", new XAttribute("prop", dup.Property),
                                                                                        new XElement("record", new XAttribute("id", dup.Value.Id)))));

                return(xres);
            });
            CreateMap <RecordWithInverses, XElement>().ConvertUsing((record, context) => record == null
                ? null
                : new XElement("record",
                               new XAttribute("id", record.Id),
                               record.Type == null ? null : new XAttribute("type", record.Type),
                               record.Fields?.Select(dup =>
                                                     new XElement("field", new XAttribute("prop", dup.Property), dup.Value)),
                               record.Directs?.Select(dup => new XElement("direct", new XAttribute("prop", dup.Property),
                                                                          new XElement("record", new XAttribute("id", dup.Value.Id)))),
                               record.Inverses?.Select(dup => new XElement("direct", new XAttribute("prop", dup.Property),
                                                                           new XElement("record", new XAttribute("id", dup.Value.Id))))));


            // ============================== Редактирование ================================
            CreateMap <Record, object>().ConvertUsing((record, context) =>
            {
                int cid = store.CodeEntity(record.Id);
                return(new object[]
                {
                    cid,
                    Enumerable.Repeat(new object[] { cod_rdftype, store.CodeEntity(record.Type) }, 1)
                    .Concat(record.Directs
                            .Select(el => new object[]
                    {
                        store.CodeEntity(el.Property),
                        store.CodeEntity(el.Value.Id)
                    })).ToArray(),
                    record.Fields
                    .Select(el => new object[]
                            { store.CodeEntity(el.Property), el.Value }).ToArray()
                });
            });

            CreateMap <XElement, Record>().ConvertUsing((xRecord, context) =>
            {
                var xAbout = xRecord.Attribute("{http://www.w3.org/1999/02/22-rdf-syntax-ns#}about");
                if (xAbout == null)
                {
                    return(null);
                }
                var props = xRecord.Elements().Select(x =>
                                                      (x,
                                                       resource: x.Attribute("{http://www.w3.org/1999/02/22-rdf-syntax-ns#}resource"),
                                                       property: "http://fogid.net/o/" + x.Name.LocalName))
                            .GroupBy(el => el.resource != null)
                            .ToArray();
                string id = xAbout.Value;
                string tp = "http://fogid.net/o/" + xRecord.Name.LocalName;
                return(new Record()
                {
                    Id = id,
                    Type = tp,
                    Fields = props.Where(g => !g.Key).SelectMany(x => x)
                             .Select(el => new RecordField
                    {
                        Property = el.property,
                        Value = el.x.Value
                    })
                             .ToArray(),
                    Directs = props.Where(g => g.Key).SelectMany(x => x)
                              .Select(el => new RecordProperty
                    {
                        Property = el.property,
                        Value = new Record
                        {
                            Id = el.resource.Value
                        }
                    }).ToArray(),
                });
            });
        }
Exemple #3
0
        public static void Main20()
        {
            System.Diagnostics.Stopwatch sw = new System.Diagnostics.Stopwatch();
            System.Random rnd = new Random();
            //string path = "../../../../data/Databases/";
            string        path      = "C:/Home/data/Databases/";
            int           fnom      = 0;
            Func <Stream> GenStream = () => File.Open(path + (fnom++), FileMode.OpenOrCreate);

            Console.WriteLine("Start TestConsoleApp (Main32)");
            TripleRecordStore store = new TripleRecordStore(GenStream, path, new string[] {
                "http://www.w3.org/1999/02/22-rdf-syntax-ns#type"
                , "http://fogid.net/o/name"
                , "http://fogid.net/o/age"
                , "http://fogid.net/o/person"
                , "http://fogid.net/o/photo-doc"
                , "http://fogid.net/o/reflection"
                , "http://fogid.net/o/reflected"
                , "http://fogid.net/o/in-doc"
            });

            int npersons     = 40_000;
            int nphotos      = npersons * 2;
            int nreflections = npersons * 6;

            bool toload = true;
            bool tocode = true;

            if (toload)
            {
                sw.Restart();
                store.Clear();
                var persons = Enumerable.Range(0, npersons).Select(i => npersons - i - 1)
                              .Select(c => new object[] { -c - 1, // Это "прямой" код не требующий кодирования через таблицу
                                                          new object[] { new object[] { 0, 3 } },
                                                          new object[] { new object[] { 1, "p" + c }, new object[] { 2, "" + 33 } } });
                var persons2 = Enumerable.Range(0, npersons).Select(i => npersons - i - 1)
                               .Select(c => store.CodeRecord(new object[] { "" + c,
                                                                            new object[] { new object[] { "http://www.w3.org/1999/02/22-rdf-syntax-ns#type", "http://fogid.net/o/person" } },
                                                                            new object[] { new object[] { "http://fogid.net/o/name", "p" + c }, new object[] { "http://fogid.net/o/age", "" + 33 } } }));
                var persons3 = Enumerable.Range(0, npersons).Select(i => npersons - i - 1)
                               .Select(c => store.CodeRecord(new object[] { "" + c, // Это "прямой" код не требующий кодирования через таблицу
                                                                            new object[] { new object[] { 0, 3 } },
                                                                            new object[] { new object[] { 1, "p" + c }, new object[] { 2, "" + 33 } } }));
                var photos = Enumerable.Range(0, nphotos).Select(i => nphotos - i - 1)
                             .Select(c => new object[] { -(c + npersons) - 1, // Это "прямой" код не требующий кодирования через таблицу
                                                         new object[] { new object[] { 0, 4 } },
                                                         new object[] { new object[] { 1, "f" + c } } });
                var photos2 = Enumerable.Range(0, nphotos).Select(i => nphotos - i - 1)
                              .Select(c => store.CodeRecord(new object[] { "" + (c + npersons),
                                                                           new object[] { new object[] { "http://www.w3.org/1999/02/22-rdf-syntax-ns#type", "http://fogid.net/o/photo-doc" } },
                                                                           new object[] { new object[] { "http://fogid.net/o/name", "f" + c } } }));
                var photos3 = Enumerable.Range(0, nphotos).Select(i => nphotos - i - 1)
                              .Select(c => store.CodeRecord(new object[] { "" + (c + npersons), // Это "прямой" код не требующий кодирования через таблицу
                                                                           new object[] { new object[] { 0, 4 } },
                                                                           new object[] { new object[] { 1, "f" + c } } }));
                var reflections = Enumerable.Range(0, nreflections).Select(i => nreflections - i - 1)
                                  .Select(c => new object[] { -(c + 3 * npersons) - 1, // Это "прямой" код не требующий кодирования через таблицу
                                                              new object[] { new object[] { 0, 5 },
                                                                             new object[] { 6, -1 - (rnd.Next(npersons)) },
                                                                             new object[] { 7, -1 - (rnd.Next(nphotos) + npersons) } },
                                                              new object[] { } });
                var reflections2 = Enumerable.Range(0, nreflections).Select(i => nreflections - i - 1)
                                   .Select(c => store.CodeRecord(new object[] { "" + (c + 3 * npersons),
                                                                                new object[] { new object[] { "http://www.w3.org/1999/02/22-rdf-syntax-ns#type", "http://fogid.net/o/reflection" },
                                                                                               new object[] { "http://fogid.net/o/reflected", "" + rnd.Next(npersons) },
                                                                                               new object[] { "http://fogid.net/o/in-doc", "" + (rnd.Next(nphotos) + npersons) } },
                                                                                new object[] { } }));
                var reflections3 = Enumerable.Range(0, nreflections).Select(i => nreflections - i - 1)
                                   .Select(c => store.CodeRecord(new object[] { "" + (c + 3 * npersons), // Это "прямой" код не требующий кодирования через таблицу
                                                                                new object[] { new object[] { 0, 5 },
                                                                                               new object[] { 6, "" + rnd.Next(npersons) },
                                                                                               new object[] { 7, "" + (rnd.Next(nphotos) + npersons) } },
                                                                                new object[] { } }));
                if (tocode)
                {
                    store.Load(persons2.Concat(photos2).Concat(reflections2));
                    //store.Load(persons3.Concat(photos3).Concat(reflections3));
                }
                else
                {
                    store.Load(persons.Concat(photos).Concat(reflections));
                }
                store.Build();
                sw.Stop();
                Console.WriteLine($"Load ok. duration={sw.ElapsedMilliseconds}");
            }
            //else
            {
                sw.Restart();
                store.Refresh();
                sw.Stop();
                Console.WriteLine($"Refresh for Phototeka {npersons} persons. Duration={sw.ElapsedMilliseconds}");
            }


            // ПОлукодирование иногда кодирование, иногда нет
            Func <int, int> HCode = nom => tocode?store.Code("" + nom) : -1 - nom;

            // Проверка
            int code = HCode(npersons * 2 / 3);

            var query1 = store.GetRecord(code);

            Console.WriteLine(store.ToTT(query1));

            // Скорость выполнения запросов
            int nprobe = 10000;

            sw.Restart();
            for (int i = 0; i < nprobe; i++)
            {
                int c  = HCode(rnd.Next(npersons));
                var ob = store.GetRecord(c);
            }
            sw.Stop();
            Console.WriteLine($"{nprobe} GetRecord() ok. duration={sw.ElapsedMilliseconds}");

            // Надо найти все фотографии, в которых отражается персона с выбранным (случайно) кодом.
            sw.Restart();
            int total = 0;

            nprobe = 1000;
            for (int i = 0; i < nprobe; i++)
            {
                int c      = HCode(rnd.Next(npersons));
                var query2 = store.GetRefers(c).Cast <object[]>().ToArray();
                var q3     = query2
                             .Select(ob => ((object[])ob[1]).Cast <object[]>()
                                     .First(dupl => (int)dupl[0] == 7));
                var q4 = q3
                         .Select(bb => store.GetRecord((int)bb[1])).ToArray();
                total += query2.Count();
            }
            sw.Stop();
            Console.WriteLine($"{nprobe} persons for photos ok. duration={sw.ElapsedMilliseconds} total={total}");

            //var likes = store.Like("p" + 666);
            //foreach (var like in likes)
            //{
            //    Console.WriteLine($"like {store.ToTT(like)}");
            //}

            sw.Restart();
            total = 0;
            for (int i = 0; i < 1000; i++)
            {
                string id = "p" + rnd.Next(npersons / 10 + 1, npersons);
                total += store.Like(id).Count();
            }
            sw.Stop();
            Console.WriteLine($"{nprobe} likes for persons ok. duration={sw.ElapsedMilliseconds} total={total}");
        }