コード例 #1
0
        public static int ReadBinary(byte[] buf, int ofs, out OsmRelation relation)
        {
            int   p = 0;
            ulong tmp;

            p += ProtoBuf.ReadVarInt(buf, ofs + p, out tmp);
            long id = (long)tmp;

            p += ProtoBuf.ReadVarInt(buf, ofs + p, out tmp);
            var values = new KeyValuePair <string, string> [tmp];

            for (int i = 0; i < values.Length; i++)
            {
                string key, val;
                p        += ProtoBuf.ReadString(buf, ofs + p, out key);
                p        += ProtoBuf.ReadString(buf, ofs + p, out val);
                values[i] = new KeyValuePair <string, string>(key, val);
            }
            p += ProtoBuf.ReadVarInt(buf, ofs + p, out tmp);
            var members = new OsmRelationMember[tmp];

            for (int i = 0; i < members.Length; i++)
            {
                p += OsmRelationMember.ReadBinary(buf, ofs + p, out members[i]);
            }
            relation = new OsmRelation(id, values, members);
            return(p);
        }
コード例 #2
0
        /// <summary>
        /// liest ein oder mehrere OSM-Relationen ein und gibt die Ergebnisse in entsprechender Reihenfolge zurück
        /// </summary>
        /// <param name="relationIds">Relations-IDs, welche abgefragt werden sollen</param>
        /// <returns>abgefragte Relationen</returns>
        public OsmRelation[] ReadRelations(params long[] relationIds)
        {
            var result = new OsmRelation[relationIds.Length];

            var searchRelations = Enumerable.Range(0, relationIds.Length).Select(i => new KeyValuePair <long, int>(relationIds[i], i)).ToArray(relationIds.Length);

            Array.Sort(searchRelations, (x, y) => x.Key.CompareTo(y.Key));

            var needBlobs = new List <OsmBlob>();
            var lastBlob  = nodeIndex[0];

            foreach (var relationId in searchRelations.Select(x => x.Key))
            {
                if (relationId > lastBlob.maxRelationId || relationId < lastBlob.minRelationId)
                {
                    lastBlob = relationIndex.BinarySearchSingle(x => relationId >= x.minRelationId && relationId <= x.maxRelationId ? 0L : x.minRelationId - relationId);
                    needBlobs.Add(lastBlob);
                }
            }

            var blobDecoder = BlobSmtDecoder(needBlobs, (blob, buf) =>
            {
                try
                {
                    OsmRelation[] tmp;
                    int len = PbfFast.DecodePrimitiveBlock(buf, 0, blob, out tmp);
                    if (len != blob.rawSize)
                    {
                        throw new PbfParseException();
                    }
                    return(tmp);
                }
                catch
                {
                    return(null);
                }
            }).GetEnumerator();

            OsmRelation[] relations    = null;
            var           tmpRelations = new List <OsmRelation[]>();

            for (int r = 0; r < searchRelations.Length; r++)
            {
                long relationId = searchRelations[r].Key;

                if (relations == null || relations[relations.Length - 1].id < relationId)
                {
                    relations = null;
                    for (int i = 0; i < tmpRelations.Count; i++)
                    {
                        if (relationId >= tmpRelations[i].First().id&& relationId <= tmpRelations[i].Last().id)
                        {
                            relations = tmpRelations[i];
                            tmpRelations.RemoveAt(i);
                            break;
                        }
                    }
                    while (relations == null)
                    {
                        blobDecoder.MoveNext();
                        relations = blobDecoder.Current;
                        if (relationId < relations.First().id || relationId > relations.Last().id)
                        {
                            tmpRelations.Add(relations);
                            relations = null;
                        }
                    }

                    Console.WriteLine("read relations: {0:N0} / {1:N0}", r + 1, searchRelations.Length);
                }

                result[searchRelations[r].Value] = relations.BinarySearchSingle(x => x.id - relationId);
            }

            return(result);
        }