TSP 問題

 投稿者:SECOND  投稿日:2014年 8月31日(日)01時25分23秒
  DEBUG ON
!---------------------------------------------------------------------
! TSP 問題 (Traveling Salesman Problem)

!---------------------------------------------------------------------
! 先日の、lark12_long さんの投稿で、紹介されていた「論文」の結果が、
! どんな物か 見る目的で、できる限り、忠実に実行してみた。
!
! 都市配置が、等辺の格子状の場合は 特別で、
! 最短コースが、目視で直視でき、それを、100% の距離として比較すると、
!
! 平均して 105% 前後の距離になるコースが、比較的 安定して得られる。
! 条件を探すと、101~102% の結果も、まれにあるが、困難。

!---------------------------------------------------------------------
! 自己組織化マップ法 (Self Organizing Maps)
! SOM による巡回セールスマン問題の解法Ⅱ (アンジェニオールのアルゴリズム)

!---------------------------------------------------------------------
! 左クリックで、中間結果の重ね書き 一時停止。 再 左クリックで継続。
! 右クリックで、強制終了。(100 都市では、500M.P3 でも 75 秒程度)
!
!2次元座標を、xy で扱うと煩雑なため、1変数の複素数で操作している。
!
!   x(i)= 都市(i)の座標          |   c(j)= node(j)の座標
!cind(i)= 都市(i)の対応node番号  |xind(j)= node(j)の対応都市番号
!                                | nac(j)= node(j)の対応都市無しの回数
!---------------------------------------------------------------------
OPTION ARITHMETIC COMPLEX
LET hw=460
LET vw=460
SET BITMAP SIZE hw+41, vw+41
SET WINDOW -20, hw+20, -20, vw+20      !左,右, 下,上
!---
SET COLOR MIX(0) 0,0,0                 !CLEAR 文で黒にする。
SET COLOR MIX(1) 1,1,1                 !text,line, 初期カラーを白にする。
SET POINT STYLE 7
SET TEXT font "",12
SET TEXT COLOR 1
LET tx0=COMPLEX(0,vw-8)                !文字列 左下端
RANDOMIZE 1
!
!------------調整項目( 定数)
LET M_=100                             !都市数
LET C_=100                             !初期 node 数 1~M_
LET G_=50                              !node 移動パラメーター
LET a_= 0.95                           !α= G_ の更新係数。G_(t+1)=α*G_(t)
LET r_=-0.2                            !γ= α の更新係数。α(t+1)=α(t)+γ/M_*(C_(t)-C_(t-1))
!
!--------------
OPTION BASE 0
LET w=M_*5                             !node 数の上限
DIM    x(M_-1)                         !都市 座標
DIM cind(M_-1)                         !都市 番号 に対する node番号
DIM xind(w)                            !node 番号 に対する 都市番号
DIM    c(w)                            !node 座標
DIM  nac(w)                            !no access counter
CALL set_grid_ini                      !都市配置が、格子状の場合の準備(hn,vn,ss1)
!
!------------調整項目( 都市 の並べ方)
CALL set_grid(x)                       !格子状 配置( 都市 )
!CALL set_circle(x)                     !サークル 配置( 都市 )
CALL shuffle(x)                        !番号シャッフル( 都市 )
!CALL set_random(x)                     !ランダム 配置( 都市 )
!
!------------調整項目( 初期 node の並べ方)
!CALL set_grid(c)                       !格子状 配置( node )
CALL set_circle(c)                     !サークル 配置( node )
!CALL shuffle(c)                        !番号シャッフル( node )
!CALL set_random(c)                     !ランダム 配置( node )
!
!----------------------------------------
! メイン
!----------------------------------------
CLEAR
CALL pl_node_run                       !都市 node 位置と、その連結線
IF 1< C_ THEN pause 1
!
MAT cind=(-1)*CON                      !都市番号 に対応する node番号 クリア
MAT xind=(-1)*CON                      !node番号 に対応する 都市番号 クリア
MAT nac=ZER                            !no access counter
LET Mcyc=0                             !都市一巡の回数
DO
   LET Cb=C_
   FOR i=0 TO C_-1
      LET nac(i)=nac(i)+1              !各 node 毎の、no access counter
   NEXT i
   FOR ss_=0 TO M_-1
      CALL Get_node                    !都市番号ss_に 最近傍node 取得
      !--
      SET DRAW mode hidden
      CLEAR
      CALL pl_node_run                 !都市位置表示と、全node の連結線
      SET DRAW mode explicit
      !--
      mouse poll mox,moy,mlb,mrb       !マウス状態取得
      IF mlbk< mlb OR 0< mrb THEN
         CALL pl_node_z                !都市位置表示と、node の対応都市+孤立node の連結線
         DO
            LET mlbk=mlb
            mouse poll mox,moy,mlb,mrb
            WAIT DELAY .03
            IF 0< mrb THEN STOP        !右クリック停止
         LOOP UNTIL mlbk< mlb          !左クリック続行
      END IF
      LET mlbk=mlb
      !--
      CALL move                        !都市番号ss_対応の 全node 移動
   NEXT ss_
   CALL Remove                         !連続3巡回、選ばれなかった node の除去
   LET G_=G_*a_                        !node 移動パラメーター G_ の更新
   LET a_=a_+r_/M_*(C_-Cb)             !更新係数 a_
   LET Mcyc=Mcyc+1                     !都市一巡の回数
   !--
   IF M_=C_ THEN LET cm_eq=cm_eq+1 ELSE LET cm_eq=0
LOOP UNTIL 1< cm_eq
CLEAR
CALL pl_node_z                         !都市位置表示と、node の対応都市+孤立node の連結線

!----------------------------------------
! 連続3巡回、選ばれなかった node の除去
!----------------------------------------
SUB Remove
   LET j=0
   FOR i=0 TO C_-1
      IF nac(i)< 3 THEN                !no access 3回未満の node を前に詰める
         LET c(j)=c(i)                 !node 座標
         LET xind(j)=xind(i)                       !対応 都市番号
         IF 0<=xind(j) THEN LET cind( xind(j))=j   !対応 都市の 対応 node番号
         LET nac(j)=nac(i)                         !no access node counter
         LET j=j+1
      END IF
   NEXT i
   LET C_=j
END SUB

!----------------------------------------
! 都市 ss_ の最近傍 node 取得
!----------------------------------------
SUB Get_node
   IF 0<=cind(ss_) THEN LET xind( cind(ss_))=-1
   LET lmin=1e9
   FOR j=0 TO C_-1
      LET l=ABS( x(ss_)-c(j) )         !都市ss_ と、各 node 間距離
      IF l< lmin THEN
         LET jc=j                      !最近傍の node 番号
         LET loc=c(j)                  !  〃     node 座標
         LET lmin=l                    !  〃     その距離
      END IF
   NEXT j
   IF 0<=xind(jc) THEN CALL add        !使用中 node の生成(複製)
   LET xind(jc)=ss_                    !node jc → 対応都市 xi
   LET nac(jc)=0                       !node jc:リセット no access node counter
   LET cind(ss_)=jc                    !都市 xi → 対応node jc
END SUB

!----------------------------------------
! node の生成
!----------------------------------------
SUB add
   LET jc=jc+1                         !複製node番号jc を後続。
   FOR i=C_-1 TO jc STEP -1            !既存node jc ~C_ を後へシフト
      LET j=i+1                        !転送元i → 転送先j
      !--
      LET c(j)=c(i)                            !node i の座標
      LET xind(j)=xind(i)                      !node i 対応都市番号
      LET nac(j)=nac(i)                        !node i:no access node counter
      IF 0<=xind(i) THEN LET cind( xind(i))=j  !node i の対応都市xind(i) → 対応node j
   NEXT i
   LET C_=C_+1
   LET c(jc)=loc                       !複製node 座標
END SUB

!----------------------------------------
! 最近傍 node と周辺の移動 更新
!
! 座標移動node(j)= node(j)+ EXP[-{node番号間数(I~j)/G_}^2] * 座標差{都市(I)-node(j)}/√2
!----------------------------------------
SUB move                                     !都市番号ss_の対応node jc と 周辺node 移動
   LET jc=cind(ss_)
   FOR j=0 TO C_-1
      LET n=MIN( MOD(jc-j,C_), MOD(j-jc,C_))
      LET fgn=EXP(-(n/G_)^2)/SQR(2)          !更新率
      LET c(j)=c(j)+fgn*( x(ss_)-c(j))
   NEXT j
END SUB

!----------------------------------------
! 描画パーツ
!----------------------------------------
! 都市位置
SUB pl_city
   FOR i=0 TO M_-1
      IF 0<=cind(i) THEN SET POINT COLOR 6 ELSE SET POINT COLOR 5
      PLOT POINTS: x(i)                !黄: 都市 with node  シアン: 都市 off node
   NEXT i
END SUB

!----都市位置表示と、node の対応都市+孤立node の連結線
SUB pl_node_z
   CALL pl_city                        !都市位置
   SET POINT COLOR 5
   FOR i=0 TO C_-1
      IF xind(i)< 0 THEN PLOT POINTS: c(i)   !対応都市の無い node のみ 位置を加える
   NEXT i
   SET LINE COLOR 5
   LET TL=0
   IF 0<=xind(0) THEN LET wb=x( xind(0)) ELSE LET wb=c(0)
   FOR i=C_-1 TO 0 STEP -1
      IF 0<=xind(i) THEN LET w=x( xind(i)) ELSE LET w=c(i)
      LET TL=TL+ABS(w-wb)
      PLOT LINES: wb;w                 !連結線
      LET wb=w
   NEXT i
   !----都市数 node数 一巡回数 距離
   PLOT label,AT tx0 ,USING "都市数=#### node数=#### 都市一巡の回数=### 距離=###.##": M_,C_,Mcyc,TL/ss1
END SUB

!----都市位置表示と、全node の連結線
SUB pl_node_run
   CALL pl_city                        !都市位置
   FOR i=0 TO C_-1
      IF 0<=xind(i) THEN SET POINT COLOR 4 ELSE SET POINT COLOR 5
      PLOT POINTS: c(i)                !赤: node with 都市  シアン: node off 都市
   NEXT i
   SET LINE COLOR 4
   FOR i=0 TO C_-1
      PLOT LINES: c(i);                !赤: 連結線 of node
   NEXT i
   PLOT LINES: c(0)
   !----都市数 node数 一巡回数
   PLOT label,AT tx0 ,USING "都市数=#### node数=#### 都市一巡の回数=###": M_,C_,Mcyc
END SUB

!---------------------------------------------------
! 都市、node の初期 配置
!---------------------------------------------------
SUB set_grid_ini                       !都市配置が、格子状の場合の準備。
   LET vn=INT( SQR(M_))                !他の配置になっても、距離の単位長 ss1 を共用。
   LET hn=vn
   IF vn*hn< M_ THEN LET hn=vn+1       !hn: 横列数 (端数列込み)
   IF vn*hn< M_ THEN LET vn=vn+1       !vn: 縦行数
   LET ss1=vw/vn                       !距離の単位長 (格子の一辺の長さ)
END SUB

SUB set_grid(a())                                !格子状配置
   IF M_< UBOUND(a) THEN LET w=C_ ELSE LET w=M_  !都市・node の識別
   LET mi=0
   FOR i=0 TO hn-1
      FOR j=0 TO vn-1
         LET a(mi)=ss1*COMPLEX(i,j)
         LET mi=mi+1
         IF w<=mi THEN EXIT SUB
      NEXT j
   NEXT i
END SUB

SUB set_circle(a())                              !サークル配置
   IF M_< UBOUND(a) THEN LET w=C_ ELSE LET w=M_  !都市・node の識別
   LET x1=x(1)
   IF x1=0 THEN                                  !都市座標が 未設定の場合は、
      LET x2=ss1*COMPLEX(hn-1,vn-1)              !広がりを、M_ の格子状とし、
   ELSE                                          !都市座標が 設定済みの場合は、
      LET x2=x1                                  !広がりの、最大最小をさがす
      FOR i=0 TO M_-1
         LET x1=COMPLEX( MIN(re(x1),re(x(i))), MIN(im(x1),im(x(i))) )
         LET x2=COMPLEX( MAX(re(x2),re(x(i))), MAX(im(x2),im(x(i))) )
      NEXT i
   END IF
   LET xc=(x1+x2)/2                              !サークル中心点
   LET ds=2*PI/w
   FOR i=0 TO w-1
      LET a(i)=xc+COMPLEX( re(x2-xc)*COS(i*ds), im(x2-xc)*SIN(i*ds) )
   NEXT i
END SUB

SUB shuffle(a())                                 !番号シャッフル
   IF M_< UBOUND(a) THEN LET w=C_ ELSE LET w=M_  !都市・node の識別
   FOR i=0 TO w-1
      LET j=INT(RND*w)
      swap a(i),a(j)
   NEXT i
END SUB

SUB set_random(a())                              !ランダム配置
   IF M_< UBOUND(a) THEN LET w=C_ ELSE LET w=M_  !都市・node の識別
   LET j=0
   DO
      LET a(j)=COMPLEX( hw*(.8*RND+.1), vw*(.8*RND+.1))
      FOR i=0 TO j-1
         IF ABS(a(i)-a(j))< 7 THEN EXIT FOR      !隣接間隔不足、再試行
      NEXT i
      IF j<=i THEN LET j=j+1
   LOOP UNTIL w<=j
END SUB

END
 

Re: TSP 問題

 投稿者:SECOND  投稿日:2014年 9月 1日(月)00時32分58秒
  > No.3476[元記事へ]

DEBUG ON
!---------------------------------------------------------------------
! TSP 問題 (Traveling Salesman Problem) の付録
!---------------------------------------------------------------------
! 先の投稿で、
! ・・都市配置が、等辺の格子状の場合は 特別で、
!   最短コースが、目視で直視でき、それを、100% の距離として・・・
! としたが、
! それを、任意な都市数 M_ で、順に表示してみるプログラム。
!
! 左クリック押し下げの間、一時停止。 右クリック終了。

!---------------------------------------------------------------------
! これを、初期 node とすれば、先のプログラムは、100% の最短距離へ
! 引き込めるけれども、node 移動パラメーター G_=1~1.4 くらいの時だけで、
! 吸引と言えるか否か、G_=40~50 では、形を失い、あまり意味はないようです。

! この実験をするには、先の投稿プログラムを以下のようにします。
!
!1)----------調整項目( 定数 )
!      LET C_=M_
!      LET G_=1~1.4
!2)----------調整項目( 都市 の並べ方)
!      CALL set_grid(x)      ← 投稿時の格子状のまま
!      CALL shuffle(x)       ←シャッフルの有無は、どちらでもよい
!3)----------調整項目( 初期 node の並べ方)
!      CALL set_grid_order(c)   ←このcall追加、他のcall停止。
!
!4)末尾に、今回の、SUB set_grid_order(x()) ~ END SUB を追加。

!---------------------------------------------------------------------
OPTION ARITHMETIC COMPLEX
LET hw=460
LET vw=460
SET BITMAP SIZE hw+41, vw+41
SET WINDOW -20, hw+20, -20, vw+20   !左,右, 下,上
!---
SET COLOR MIX(0) 0,0,0              !CLEAR 文で黒にする。
SET COLOR MIX(1) 1,1,1              !text,line, 初期カラーを白にする。
SET POINT STYLE 7
SET TEXT font "",14
SET TEXT COLOR 1
LET tx0=COMPLEX(0,vw-8)             !文字列 左下端
!
OPTION BASE 0
DIM x(600)                          !都市 座標
!
!----------------------------------------
! メイン
!----------------------------------------
FOR M_=100 TO 1 STEP -1               !M_= 都市数
   LET vn=INT( SQR(M_) )
   LET hn=vn
   IF vn*hn< M_ THEN LET hn=vn+1      !hn: 横列数 (端数列込み)
   IF vn*hn< M_ THEN LET vn=vn+1      !vn: 縦行数
   ! LET ss1=vw/vn                      !距離の単位長 (格子の一辺の長さ) ※M_ が昇順の時。
   IF ss1=0 THEN LET ss1=vw/vn        !距離の単位長 (格子の一辺の長さ) ※最初の幅を固定
   !--
   CALL set_grid_order(x)             !格子状配置 最短距離コース
   !--
   SET DRAW mode hidden
   CLEAR
   CALL pl_city_sts                   !表示
   SET DRAW mode explicit
   LET i=0
   DO
      mouse poll mox,moy,mlb,mrb
      IF mrb=1 THEN EXIT FOR
      LET i=i+1-mlb
      WAIT DELAY .05
   LOOP UNTIL 18<=i
NEXT M_

!----------------------------------------
! 描画
!----------------------------------------
SUB pl_city_sts             !都市と、その連結線
   SET POINT COLOR 6
   SET LINE COLOR 5
   LET TL=0
   LET wb=x(0)
   FOR i=M_-1 TO 0 STEP -1
      LET w=x(i)
      PLOT POINTS: w
      PLOT LINES: wb;w
      LET TL=TL+ABS(w-wb)
      LET wb=w
   NEXT i
   !----都市数 距離
   PLOT label,AT tx0 ,USING "都市数=#### 距離=###.##": M_,TL/ss1
END SUB

!-------------------------------
! 都市 格子状配置 最短距離コース
!-------------------------------

!--+----------------------------+------------------------
! ! 横:偶数         ! 横:奇数
!--+----------------------------+------------------------
! !・・・・・・ ┌┐┌┐┌┐ !・・・・・ ┌┐┌→┐
! !・・・・・・ ↑↓↑↓↑↓ !・・・・・ ↑↓↑┌┘
! !・・・・・・ ↑└┘└┘↓ !・・・・・ ↑└┘└┐
! !・・・・・・ └←←←←┘ !・・・・・ └←←←┘
! !              !
!縦!・・・・・  ┌┐┌┐ <  !・・・・  ┌┐┌ <
! !・・・・・・ ↑↓↑↓↑>  !・・・・・ ↑↓↑┌>
!偶!・・・・・・ ↑└┘└┘↓ !・・・・・ ↑└┘└┐
!数!・・・・・・ └←←←←┘ !・・・・・ └←←←┘
! !              !
! !・・・・・  ┌┐┌→┐  !・・・・  ┌┐┌┐
! !・・・・・  ↑↓↑┌┘  !・・・・  ↑↓↑↓
! !・・・・・・ ↑└┘└→┐ !・・・・・ ↑└┘└┐
! !・・・・・・ └←←←←┘ !・・・・・ └←←←┘
! !              !
! !・・・・・  ┌┐┌→┐  !・・・・  ┌┐┌┐  !・・・・ ┌┐┌┐
! !・・・・・  ↑↓↑┌┘  !・・・・  ↑↓↑↓  !・・・・ ↑↓↑↓
! !・・・・・  ↑└┘└ <  !・・・・  ↑└┘ <  !・・・・ ↑└┘↓
! !・・・・・・ └←←←←>  !・・・・・ └←←←>  !・・・・ └←←┘
!--+----------------------------+------------------------
! ! 横:偶数         ! 横:奇数
!--+----------------------------+------------------------
! !・・・・・・ ┌┐┌┐┌┐ !・・・・・ ┌┐┌→>
! !・・・・・・ ↑↓↑↓↑↓ !・・・・・ ↑↓↑ <┐
! !・・・・・・ ↑↓↑↓↑↓ !・・・・・ ↑↓↑┌┘
! !・・・・・・ ↑└┘└┘↓ !・・・・・ ↑└┘└┐
! !・・・・・・ └←←←←┘ !・・・・・ └←←←┘
! !              !
!縦!・・・・・  ┌┐┌┐ <  !・・・・  ┌┐┌┐
! !・・・・・・ ↑↓↑↓↑>  !・・・・・ ↑↓↑└┐
!奇!・・・・・・ ↑↓↑↓↑↓ !・・・・・ ↑↓↑┌┘
!数!・・・・・・ ↑└┘└┘↓ !・・・・・ ↑└┘└┐
! !・・・・・・ └←←←←┘ !・・・・・ └←←←┘
! !              !
! !・・・・・  ┌┐┌→┐  !・・・・  ┌┐┌┐
! !・・・・・  ↑↓↑┌┘  !・・・・  ↑↓↑ <
! !・・・・・・ ↑↓↑↓┌┐ !・・・・・ ↑↓↑┌>
! !・・・・・・ ↑└┘└┘↓ !・・・・・ ↑└┘└┐
! !・・・・・・ └←←←←┘ !・・・・・ └←←←┘
! !              !
! !・・・・・  ┌┐┌→┐  !・・・・  ┌┐┌┐
! !・・・・・  ↑↓↑┌┘  !・・・・  ↑↓↑↓
! !・・・・・  ↑↓↑↓ <  !・・・・  ↑↓↑↓
! !・・・・・・ ↑└┘└┘>  !・・・・・ ↑└┘└┐
! !・・・・・・ └←←←←┘ !・・・・・ └←←←┘
! !--------- 特2/------------!
! !・・・・・  ┌┐┌→>   !・・・・  ┌┐┌┐  !・・・・ ┌┐┌┐
! !・・・・・  ↑↓↑ <┐  !・・・・  ↑↓↑↓  !・・・・ ↑↓↑↓
! !・・・・・  ↑↓↑┌┘  !・・・・  ↑↓↑↓  !・・・・ ↑↓↑↓
! !・・・・・  ↑└┘└ <  !・・・・  ↑└┘ <  !・・・・ ↑└┘↓
! !・・・・・・ └←←←←>  !・・・・・ └←←←>  !・・・・ └←←┘
!--+----------------------------+------------------------

SUB set_grid_order(x())
   LET rn=MOD(M_,vn)                  !rn: 右端列 の端数
   IF rn=0 THEN LET rn=vn             !    (端数0不可)
   !--
   LET mi=0
   LET i=0
   FOR j=0 TO vn-1                    !・
      LET x(mi)=ss1*COMPLEX(i,j)      !↑
      LET mi=mi+1                     !・
   NEXT j
   LET i=i+1
   !--
   IF MOD(hn,2)=0 THEN
   !--------------------------------------------横:even
      DO WHILE i< hn-2
         LET j=vn-1                             !→・
         IF i=hn-3 THEN
         !--
            IF MOD(vn,2)=0 THEN
            !-----------------------------------横:even 縦:even
               LET w=CEIL(rn/2)*2   !2,2,4,4,6,6
            ELSE
            !-----------------------------------横:even 縦:odd
               LET w=INT(rn/2)*2+1  !1,3,3,5,5,7,7
               !--
               IF rn=1 THEN
                  LET x(mi)=ss1*COMPLEX(i,j)    !・
                  LET mi=mi+1
                  LET x(mi)=ss1*COMPLEX(i+1,j)  !→
                  LET mi=mi+1
                  LET j=j-1
               END IF
            END IF
            !--
            LET d=1
            FOR j=j TO w STEP -1
               LET x(mi)=ss1*COMPLEX(i,j)       !・
               LET mi=mi+1
               LET i=i+d
               LET x(mi)=ss1*COMPLEX(i,j)       !←→
               LET mi=mi+1
               LET d=-d
            NEXT j
         END IF
         !--
         LET w=j
         FOR j=j TO 1 STEP -1                   !→・
            LET x(mi)=ss1*COMPLEX(i,j)          ! ↓
            LET mi=mi+1                         ! ・
         NEXT j
         LET i=i+1
         !--
         IF i< hn-2 AND 0< w THEN LET w=vn-1    ! ・
         FOR j=1 TO w                           ! ↑
            LET x(mi)=ss1*COMPLEX(i,j)          !→・
            LET mi=mi+1
         NEXT j
         LET i=i+1
      LOOP
      !--
      FOR j=rn-1 TO 1 STEP -1                   !→・
         LET x(mi)=ss1*COMPLEX(i,j)             ! ↓
         LET mi=mi+1                            ! ・
      NEXT j
   ELSE
   !--------------------------------------------横:odd
      DO WHILE i< hn-3
         FOR j=vn-1 TO 1 STEP -1                !→・
            LET x(mi)=ss1*COMPLEX(i,j)          ! ↓
            LET mi=mi+1                         !
         NEXT j
         LET i=i+1
         FOR j=1 TO vn-1                        ! ・
            LET x(mi)=ss1*COMPLEX(i,j)          !→↑
            LET mi=mi+1                         !
         NEXT j
         LET i=i+1
      LOOP
      !--
      FOR j=vn-1 TO rn STEP -1                  !→・
         LET x(mi)=ss1*COMPLEX(i,j)             ! ↓
         LET mi=mi+1                            !
      NEXT j
      !--
      LET d=1
      FOR j=j TO 1 STEP -1
         LET x(mi)=ss1*COMPLEX(i,j)             !・
         LET mi=mi+1
         LET i=i+d
         LET x(mi)=ss1*COMPLEX(i,j)             !←→
         LET mi=mi+1
         LET d=-d
      NEXT j
   END IF
   FOR i=hn-1 TO 1 STEP -1            !
      LET x(mi)=ss1*COMPLEX(i,j)      !
      LET mi=mi+1                     !←・
   NEXT i
END SUB

END
 

戻る