Как обновить массив после BubbleSort - asm в vc ++ - PullRequest
0 голосов
/ 06 марта 2011

Сейчас я изучаю основы сортировки пузырьков в ассемблере, и то, что я кодировал, имеет смысл в моей голове, но, видимо, не для компилятора. Когда я распечатываю весь массив после выполнения этой подпрограммы, почему массив выглядит так же, как до сортировки?

bubblesort proc

    bubbleSort Proc

mov ecx, NUMS_LENGTH
dec ecx
mov edi, 0

 .WHILE ecx > 0
    mov ax, NUMS[di]    
        .IF ax > NUMS[di]+2
            xchg ax, NUMS[di]+2
            call WriteInt
            mov [NUMS[di]+2], ax
            inc di
        .ENDIF
    dec ecx
.ENDW

bubbleSort endp

Советы и понимание очень ценятся. Большое спасибо заранее!

EDIT

bubbleSort Proc

mov ecx, NUMS_LENGTH
dec ecx
mov edi, 0

.WHILE ecx > 0
    mov di, NUMS_LENGTH-1
    .WHILE di < NUMS_LENGTH-1
            mov ax, NUMS[di]
        .IF ax > NUMS[di]+2
            xchg ax, NUMS[di]+2
            mov [NUMS[di]+2], ax
            inc di
        .ELSE
            inc di
        .ENDIF
    .ENDW
    dec ecx
.ENDW

bubbleSort endp

* РЕДАКТИРОВАТЬ 2 *

bubbleSort Proc

mov ecx, NUMS_LENGTH
dec ecx
mov di, 0


.WHILE ecx > 0
        mov ax, NUMS[di]
    .WHILE di != NUMS_LENGTH-1

        .IF ax > NUMS[di]+2
            xchg ax, NUMS[di]+2
            mov NUMS[di]+2, ax
            inc di
        .ELSE
            inc di
            mov NUMS[di]+2, ax
        .ENDIF
    .ENDW
    dec ecx
.ENDW

bubbleSort endp

1 Ответ

1 голос
/ 06 марта 2011

Похоже, это не выглядит совсем одинаково, но оно также не отсортировано.

Пузырьковая сортировка требует двух вложенных циклов, но, похоже, у вас есть только один цикл. Это означает, что он делает только один проход через массив. В конце одного прохода последний элемент в массиве будет в правильной позиции, но остальные еще не будут отсортированы.

Редактировать: отредактированный код, вероятно, не является улучшением. В частности:

mov di, NUMS_LENGTH-1
.WHILE di < NUMS_LENGTH-1

Мы устанавливаем di равным NUMS_LENGTH-1, затем выполняем цикл while, который может выполняться, только если di меньше NUMS_LENGTH-1, так что внутренний цикл явно (никогда!) Не будет выполняться.

Edit2: Хотя пузырьковая сортировка на ассемблере кажется мне едва ли не худшей из возможных времен, я полагаю, если вы настаиваете, очевидный способ начать - рассмотреть, как выглядит пузырьковая сортировка в чем-то вроде C:

for (int i=array_len; i!=0; --i)
    for (int j=0; j<i; j++)
        if (array[j] > array[j+1]) {
            temp = array[j];
            array[j] = array[j+1];
            array[j+1] = temp;
        }

Написание чего-либо в том же общем порядке на ассемблере не должно быть очень сложным.

Edit4: исправлен код (я думаю):

    mov ecx, (NUMS_LEN-1)*4
outer_loop:
    xor edi, edi
inner_loop:
    mov eax, nums[edi]
    cmp eax, nums[edi+4]
    jl noswap
    xchg nums[edi+4], eax
    mov nums[edi], eax
noswap:
    add edi, 4
    cmp edi, ecx
    jl inner_loop
    sub ecx, 4
    jnz outer_loop

Извините - я так и не привык к макросам потока управления "высокого уровня" Microsoft для языка ассемблера. Несколько моментов для рассмотрения: по крайней мере, предполагая, что мы не допускаем массив нулевой длины, для этой задачи циклы, которые проверяют условие внизу, намного проще. В общем, петли, которые тестируются внизу, в любом случае более понятны на ассемблере. Когда алгоритм требует теста в начале, все еще часто бывает проще поставить тест внизу и построить структуру вроде:

   initalization 
   jmp loop_test
loop_top:
   loop body
loop_test:
    update loop variable(s)
    if (more iterations)
        jmp loop_top
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...