/// <summary>
        /// 自己位置推定計算
        /// </summary>
        /// <param name="LRF_Data">LRF実取得データ</param>
        /// <param name="MRF">MAPデータ</param>
        /// <param name="mkp">想定ロボット位置(計算基点)</param>
        /// <param name="Particles">パーティクル作業バッファ</param>
        public void Localize(double[] LRF_Data, MapRangeFinder MRF, MarkPoint mkp, List<Particle> Particles)
        {
            double sum = 0;

            if (null == LRF_Data)
            {
                Console.WriteLine("ParticleFilter.cs Localize() : Error! null LrfData");
                return;
            }

            // パーティクルをばらまく
            //for (int i = 0; i < Particles.Count; ++i)
            int numParticles = Particles.Count;
            Parallel.For(0, numParticles, i =>

                {
                    // 散らばらせる
                    MakeParticle(mkp, PtclRange, PtclDirRange, Particles[i].Location);

                    // 散らばり% = w ?
                    // マップデータとLRFのデータを比べる
                    Particles[i].W = Likefood(LRF_Data, MRF.Sense(Particles[i].Location));
                    sum += Particles[i].W;
                });

            // W順に並べ替え
            Particles.Sort((a, b) => (int)((a.W - b.W)*1000.0));

            // パーティクルから 整合性の高いデータを取り出す?(リサンプリング)
            for (int n = 0; n < ResamplingNumber; ++n)
            {
                double selectVal = Rand.NextDouble() * sum;
                double subsum = 0;
                for (int i = 0; i < Particles.Count; ++i)
                {
                    subsum += Particles[i].W;
                    if (selectVal < subsum)
                    {
                        ResamplingSet[n] = Particles[i].Location;
                        break;
                    }
                }
            }

            // パーティクルの平均値から、仮想ロボットの位置を補正
            double newX = 0;
            double newY = 0;
            double newTheta = 0;
            for (int n = 0; n < ResamplingNumber; ++n) {
                newX += ResamplingSet[n].X;
                newY += ResamplingSet[n].Y;
                newTheta += ResamplingSet[n].Theta;
            }

            mkp.X = newX / ResamplingNumber;
            mkp.Y = newY / ResamplingNumber;
            mkp.Theta = newTheta / ResamplingNumber;
        }
Example #2
0
        /// <summary>
        /// 自己位置推定  開始位置セット
        /// </summary>
        /// <param name="stWldX">マップ座標X</param>
        /// <param name="stWldY">マップ座標Y</param>
        /// <param name="stDir">角度</param>
        public void SetStartPostion(int stWldX, int stWldY, double stDir)
        {
            startMapX   = stWldX;
            startMapY   = stWldY;
            startMapDir = stDir;

            MRF = new MapRangeFinder(LRF_Ctrl.LRFmaxRange_mm / MapToRealScale);    // 仮想Map用 LRFクラス

            worldMap.UpdateAreaCenter(stWldX, stWldY);
            AreaBmp = worldMap.AreaGridMap.UpdateBitmap();
            //bAreaMapUpdateReqest = false;

            MRF.SetMap(worldMap.AreaGridMap);

            // ロボットマーカ設定
            R1 = new MarkPoint(stWldX, stWldY, stDir);    // 実ロボット位置 R.E,Compass,GPSでの位置+ LRF補正

            E1    = new MarkPoint(stWldX, stWldY, stDir); // R.Encoderの位置
            oldE1 = new MarkPoint(stWldX, stWldY, stDir); //

            E2 = new MarkPoint(stWldX, stWldY, stDir);    // R.E Pluse & Compus の位置

            V1    = new MarkPoint(stWldX, stWldY, stDir); // 推定位置ロボット
            C1    = new MarkPoint(0, 0, stDir);
            G1    = new MarkPoint(0, 0, 0);               // GPS
            oldG1 = new MarkPoint(stWldX, stWldY, stDir); //

            A1 = new MarkPoint(0, 0, 0);                  // AMCL

            // パーティクルフィルター初期化
            {
                // サンプル数(ParticleSizeと同じで、すべてのパーティクルを対象とする)
                // LRFの有効距離を半径に変換(/2.0)、20%の距離で散らばる
                // +-5度の範囲
                ParticleFilter = new ParticleFilter(ParticleSize, (((LRF_Ctrl.LRFmaxRange_mm / 2.0) * 0.20) / MapToRealScale), 30.0);         // サンプリング数、パーティクルのレンジ

                Particles = new List <Particle>();
                for (int i = 0; i < ParticleSize; ++i)
                {
                    // パーティクルマーカー
                    Particles.Add(new Particle(new MarkPoint(0, 0, 0), 0));
                }
            }

            // ローパスフィルター初期化
            ResetLPF_V1(V1);
        }
Example #3
0
 /// <summary>
 /// MAP初期化
 /// </summary>
 /// <param name="fname"></param>
 public void MapInit(Bitmap mapBmp)
 {
     // 30m
     mrf = new MapRangeFinder((30 * 1000), PixelScale, mapBmp);
 }
        /// <summary>
        /// 自己位置推定計算
        /// </summary>
        /// <param name="LRF_Data">LRF実取得データ</param>
        /// <param name="MRF">MAPデータ</param>
        /// <param name="mkp">想定ロボット位置(計算基点)</param>
        /// <param name="Particles">パーティクル作業バッファ</param>
        public void Localize(double[] LRF_Data, MapRangeFinder MRF, MarkPoint mkp, List <Particle> Particles)
        {
            double sum = 0;

            if (null == LRF_Data)
            {
                Console.WriteLine("ParticleFilter.cs Localize() : Error! null LrfData");
                return;
            }

            // パーティクルをばらまく
            //for (int i = 0; i < Particles.Count; ++i)
            int numParticles = Particles.Count;

            Parallel.For(0, numParticles, i =>

            {
                // 散らばらせる
                MakeParticle(mkp, PtclRange, PtclDirRange, Particles[i].Location);

                // 散らばり% = w ?
                // マップデータとLRFのデータを比べる
                Particles[i].W = Likefood(LRF_Data, MRF.Sense(Particles[i].Location));
                sum           += Particles[i].W;
            });

            // W順に並べ替え
            Particles.Sort((a, b) => (int)((a.W - b.W) * 1000.0));

            // パーティクルから 整合性の高いデータを取り出す?(リサンプリング)
            for (int n = 0; n < ResamplingNumber; ++n)
            {
                double selectVal = Rand.NextDouble() * sum;
                double subsum    = 0;
                for (int i = 0; i < Particles.Count; ++i)
                {
                    subsum += Particles[i].W;
                    if (selectVal < subsum)
                    {
                        ResamplingSet[n] = Particles[i].Location;
                        break;
                    }
                }
            }

            // パーティクルの平均値から、仮想ロボットの位置を補正
            double newX     = 0;
            double newY     = 0;
            double newTheta = 0;

            for (int n = 0; n < ResamplingNumber; ++n)
            {
                newX     += ResamplingSet[n].X;
                newY     += ResamplingSet[n].Y;
                newTheta += ResamplingSet[n].Theta;
            }

            mkp.X     = newX / ResamplingNumber;
            mkp.Y     = newY / ResamplingNumber;
            mkp.Theta = newTheta / ResamplingNumber;
        }
        /// <summary>
        /// 自己位置推定  開始位置セット
        /// </summary>
        /// <param name="stWldX">マップ座標X</param>
        /// <param name="stWldY">マップ座標Y</param>
        /// <param name="stDir">角度</param>
        public void SetStartPostion(int stWldX, int stWldY, double stDir)
        {
            MRF = new MapRangeFinder(LRF_Ctrl.LRFmaxRange_mm / MapToRealScale);    // 仮想Map用 LRFクラス

            worldMap.UpdateAreaCenter(stWldX, stWldY);
            AreaBmp = worldMap.AreaGridMap.UpdateBitmap();
            //bAreaMapUpdateReqest = false;

            MRF.SetMap(worldMap.AreaGridMap);

            // ロボットマーカ設定
            R1 = new MarkPoint(stWldX, stWldY, stDir);        // 実ロボット位置 R.E,Compass,GPSでの位置+ LRF補正

            E1 = new MarkPoint(stWldX, stWldY, stDir);        // R.Encoderの位置
            oldE1 = new MarkPoint(stWldX, stWldY, stDir);     //

            E2 = new MarkPoint(stWldX, stWldY, stDir);        // R.E Pluse & Compus の位置

            V1 = new MarkPoint(stWldX, stWldY, stDir);        // 推定位置ロボット
            C1 = new MarkPoint(0, 0, stDir);
            G1 = new MarkPoint(0, 0, 0);        // GPS
            oldG1 = new MarkPoint(stWldX, stWldY, stDir);     //

            // パーティクルフィルター初期化
            {
                // サンプル数(ParticleSizeと同じで、すべてのパーティクルを対象とする)
                // LRFの有効距離を半径に変換(/2.0)、20%の距離で散らばる
                // +-5度の範囲
                ParticleFilter = new ParticleFilter(ParticleSize, (((LRF_Ctrl.LRFmaxRange_mm / 2.0) * 0.20) / MapToRealScale), 30.0 );        // サンプリング数、パーティクルのレンジ

                Particles = new List<Particle>();
                for (int i = 0; i < ParticleSize; ++i)
                {
                    // パーティクルマーカー
                    Particles.Add(new Particle(new MarkPoint(0,0,0), 0));
                }
            }

            // ローパスフィルター初期化
            ResetLPF_V1(V1);
        }