技术开发 频道

Eight Queens algorithm With ABAP

【IT168 技术文章】

    If you have time and interest in eight queens algorithm, then you can read this article, it is done by ABAP and tested in ECC6.
 

    REPORT z_8queen NO STANDARD PAGE HEADING.

    
*Store where the queen is
    DATA: BEGIN OF row ,
               val TYPE i,
             END OF row .
    DATA: i_row LIKE row OCCURS
0 WITH HEADER LINE .

    
*How many ways we can achieve
    DATA: oktimes TYPE i .
    data: queen type i.

    
*Define the number of queen
    CONSTANTS: queenmax TYPE i VALUE
8 .

    
*Input queen number
    PARAMETERS: p_num TYPE i DEFAULT queenmax.

    

    START
-OF-SELECTION .
      PERFORM main_process .

    
*&---------------------------------------------------------------------*
    
*& Form MAIN_PROCESS
    
*&---------------------------------------------------------------------*
    
* text
    
*----------------------------------------------------------------------*
    FORM main_process .
      DATA: l_num TYPE i .
"The first place
      DATA: l_s(50) TYPE c . "Output string
      DATA: l_time(10) TYPE c.

      queen
= p_num + 1.
    
* Init place table
      DO queenmax TIMES .
        i_row
-val = -1 .
        APPEND i_row .
      ENDDO.
      l_num
= 1 .
    
* recursion
      PERFORM place_queen USING l_num.

    
* Get ways of algorithm

      l_time
= oktimes .
      CONDENSE l_time .
      CONCATENATE
'Eight Queens have' l_time 'ways to solve it.' INTO l_s
      SEPARATED BY space.
      WRITE: l_s .
    ENDFORM.
" MAIN_PROCESS
    *&---------------------------------------------------------------------*
    
*& Form place_queen
    
*&---------------------------------------------------------------------*
    
* text
    
*----------------------------------------------------------------------*
    FORM place_queen USING p_num.
    
* Local data definition
      DATA: l_i TYPE i .
      DATA: l_num TYPE i .
    
* Temp variants
      DATA: l_k TYPE i .
      DATA: l_t1 TYPE i .
      DATA: l_t2 TYPE i .

    
* Safe place
      DATA: BEGIN OF qsave OCCURS
0 ,
        val TYPE i ,
      END OF qsave .

    
* Init safe place, make all place be safe
      DO queenmax TIMES .
        qsave
-val = 1 .
        APPEND qsave .
      ENDDO.

      l_i
= 1 .
      l_num
= p_num .

    
* This loop get the safe place
      WHILE l_i
< l_num .
        READ TABLE i_row INDEX l_i .
        READ TABLE qsave INDEX i_row
-val .
        qsave
-val = 0 .
        MODIFY qsave INDEX i_row
-val.

        l_k
= l_num - l_i .
        l_t1
= i_row-val + l_k .
        l_t2
= i_row-val - l_k .

    
* Mark safe place
    
* If a queen's place is I_ROW[i]=j, then the unsafe place is row k column j
    * and column j+k-i and j-k+i


        IF l_t1
>= 1 AND l_t1 < queen .
          READ TABLE qsave INDEX l_t1 .
          qsave
-val = 0 .
          MODIFY qsave INDEX l_t1 .
        ENDIF.

        IF l_t2
>= 1 AND l_t2 < queen .
          READ TABLE qsave INDEX l_t2 .
          qsave
-val = 0 .
          MODIFY qsave INDEX l_t2 .
        ENDIF.
        l_i
= l_i + 1 .
      ENDWHILE .

      l_i
= 1 .
    
* Below loop is to get the queen's place
      WHILE l_i < queen .
        READ TABLE qsave INDEX l_i .
        IF qsave
-val = 0 .
    
* If this place is not safe, then get the next place
          l_i
= l_i + 1 .
          CONTINUE .
        ENDIF.

    
* if not the last place
        IF p_num
< queenmax.
          READ TABLE i_row INDEX p_num .
          i_row
-val = l_i .
          MODIFY i_row INDEX p_num .
          l_num
= p_num + 1 .
    
* Get the next queen's place
          PERFORM place_queen USING l_num .
        ELSE .
    
* The last queen, give her the last place
          READ TABLE i_row INDEX p_num .
          i_row
-val = l_i .
          MODIFY i_row INDEX p_num.
    
* The ways of place add 1 and output
          oktimes
= oktimes + 1 .
          WRITE:
'--------------------------------------------------------------------------------',/.
          LOOP AT i_row .
            WRITE: i_row
-val .
          ENDLOOP .
          WRITE:
/ .
        ENDIF.
        l_i
= l_i + 1 .
      ENDWHILE .
    ENDFORM.
" PLACE_QUEEN
0
相关文章