Ερώτηση για αρνητικούς αριθμούς

συζητήσεις για assembly

Συντονιστές: WebDev Moderators, Super-Moderators

Απάντηση
kkkkonstantina
Δημοσιεύσεις: 14
Εγγραφή: 12 Νοέμ 2009 17:49

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από kkkkonstantina » 06 Δεκ 2011 00:13

Αντιμετωπίζω μια δυσκολία!
Πως διαβάζουμε αρνητικούς αριθμούς από το πληκτρολόγιο ?? Θέλω να κάνω έναν πίνακα και να περνάω αρνητικούς αριθμούς από το πληκτρολόγιο!Όταν πάω να το γράψω το (-) το παίρνει ως ένα στοιχείο του Πίνακα

nkast
Δημοσιεύσεις: 137
Εγγραφή: 15 Νοέμ 2009 20:31
Επικοινωνία:

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από nkast » 06 Δεκ 2011 02:28

Δηλαδή τους θετικους πως τους διαβασεις;
Αν διαβαζεις εναν χαρακτηρα και μετα αφαιρείς 30h τοτε μαθε πως αυτο ειναι ενα γρηγορο hack.

Το πιο σωστο είναι να διαβασεις την είσοδο σαν αλφαριθμητικό και μετα να τον μετατρεψεις.

Δώσε κώδικα και βλέπουμε.
Αν θελεις να φτιαξεις κατι σαν calculator τοτε οταν διαβαζεις '-' , μπορεις να το κρατας σε μια μεταβλητη και να ξαναπροσπαθείς να διαβασεις αριθμο.

kkkkonstantina
Δημοσιεύσεις: 14
Εγγραφή: 12 Νοέμ 2009 17:49

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από kkkkonstantina » 06 Δεκ 2011 07:07

Σύμφωνα με αυτές τις εντολές διαβάζουμε έναν αριθμό και τον μετατρέπουμε σε κώδικα ascii όμως δεν μπορώ να βρω κάποιο τρόπο να διαβάσω τον αρνητικό, πρέπει να χρησιμοποιήσω push και pop?

Κώδικας: Επιλογή όλων


;anagnwsi xaraktira apo to plhktrologio
mov AH,1     
int 21h

;,etatropi xaraktira se arithmo,estw dld oti tou dinoume tn arithmo 1 
;kanei ('1'-30h)=31h-30h=1
mov DL, AL 
sub DL, 30h
mov [SI],DL
Εδώ είναι η εμφάνιση του αριθμού:

Κώδικας: Επιλογή όλων

 

emfanisi:

mov AX,0
mov AL,[SI]
mov DX,AX
mov DI,X
add DI,2

L2:

mov AX,DX
mov DX,0
mov BX,10
div BX

xchg AX,DX
add AL,30H
mov [DI],AL

dec DI
cmp DX,0
jnz L2

mov AH,09
mov DX,X
int 21h

mov AH,09
mov DX,keno
int 21h

inc SI
mov DI,0

loop emfanisi

nkast
Δημοσιεύσεις: 137
Εγγραφή: 15 Νοέμ 2009 20:31
Επικοινωνία:

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από nkast » 06 Δεκ 2011 12:12

Αυτο δουλεύει μόνο με αριθμούς απο 0 εως 9. Δεν σε πειράζει;

kkkkonstantina
Δημοσιεύσεις: 14
Εγγραφή: 12 Νοέμ 2009 17:49

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από kkkkonstantina » 06 Δεκ 2011 18:50

Όχι είναι μόνο για μονοψήφιους αριθμούς, αλλά τελικά επειδή έχει πολύ διαδικασία (πρέπει να διαβάζει τον αρνητικό και να δεσμεύει 2 θέσεις στον πίνακα κ έπειτα να κάνουμε συμπλήρωμα ως προς 2), μας είπε να έχουμε περασμένους ήδη κάποιους αρνητικούς αριθμούς στον πίνακα οπότε λύθηκε το πρόβλημα! Ευχαριστώ που ασχολήθηκες :-).
Επειδή θα έχω κ να μετρήσω πλήθος μέσα σε πίνακα αν κάπου αντιμετωπίσω δυσκολία θα ήταν super αν μπορείς κ ξέρεις να με βοηθήσεις ! Κ πάλι ευχαριστώ!

nkast
Δημοσιεύσεις: 137
Εγγραφή: 15 Νοέμ 2009 20:31
Επικοινωνία:

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από nkast » 07 Δεκ 2011 19:19

Εχω ερκετα χρονια να ασχοληθώ (δεν εχω καν εγκατεστημενo asm) οποτε το παρακατω αντιμετωπισε το σαν psedocode. Δεν ξερω αν θα τρεχει σωστα. Θα χρειαστει ισως να καταλαβεις την ιδεα και να το διορθώσεις αν χρειαστεί.

Κώδικας: Επιλογή όλων

;anagnwsi xaraktira apo to plhktrologio
;epitreptes times 0-9 kai '-'  
mov AH,1 
int 21h
cmp AL,'-'
jnz metatropi:

;anagnwsi xaraktira apo to plhktrologio
;anamenomenes times 0-9 
mov AH,1 
int 21h

;metatropi xaraktira se arnitiko arithmo
mov DL, AL 
sub DL, 30h 
not DL ; flip bits
inc DL ; add 1
mov [SI],DL
jmp mfanisi


;metatropi xaraktira se arithmo,estw dld oti tou dinoume tn arithmo 1 
;kanei ('1'-30h)=31h-30h=1 
metatropi:
mov DL, AL 
sub DL, 30h 
mov [SI],DL

mfanisi:
...

nkast
Δημοσιεύσεις: 137
Εγγραφή: 15 Νοέμ 2009 20:31
Επικοινωνία:

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από nkast » 07 Δεκ 2011 19:36

Δες και το παρακάτω.
Μπορείς να καταλάβεις τι ακριβώς κάνει;

Κώδικας: Επιλογή όλων

mov BX,SP ; save stack position
mov AL,'$' ; mark
push AL

:readcharacher
mov AH,1 
int 21h 
push AL
cmp AL,13h
jnz readcharacher


;emfanisi tou periexomenou tou stack
mov AH,09 
mov DX,SP 
int 21h

;restore stack
mov SP,BX

LightForce
WebDev Moderator
Δημοσιεύσεις: 3812
Εγγραφή: 13 Απρ 2003 23:49

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από LightForce » 08 Δεκ 2011 01:42

nkast υπόψην δεν μπορείς απευθείας να 'σπρώξεις' 8 bit καταχωρητή στην στοίβα σε intel αρχιτεκτονική. To νόημα όπως φαίνεται :)

Κώδικας: Επιλογή όλων

 push AL 

kkkkonstantina έγραψα πρόχειρα λίγες μικρές ρουτίνες, ίσως σου φανούν χρήσιμες.
Είναι απλοικές χωρίς ελέγχους και προυποθέτουν σωστή εισαγωγή στοιχείων. Θα τρέξουν σε fasm.

Η newline() τυπώνει CR+LF.
Η putc() τυπώνει έναν χαρακτήρα.
H puts() τυπώνει null-terminated string.
H putsint() τυπώνει έναν προσημασμένο 16-bit δεκαδικό.
H putint() τυπώνει έναν μη προσημασμένο 16-bit δεκαδικό.
Η gets() διαβάζει και αποθηκεύει null-terminated string (Δες: INT 21h / AH=0A)
Η atoi() μετατρέπει null-terminated string σε binary.

Κώδικας: Επιλογή όλων

;--------------------------------
; print CR+LF
newline:
        push ax
        mov al, 13
        call putc
        mov al, 10
        call putc
        pop ax
        ret

;--------------------------------
; AL = character
putc:
        push ax
        mov ah, 0Eh
        int 10h
        pop ax
        ret

;--------------------------------
; SI = string
puts:
        push ax si
        cld
.L1:    lodsb
        cmp al, 0
        jz .L0
        call putc
        jmp .L1
.L0:    pop si ax
        ret

;--------------------------------
; AX = signed integer
putsint:
        cmp ax, 0
        jns .L1
        push ax
        mov al, '-'
        call putc
        pop ax
        neg ax
.L1:    call putint
        ret

;--------------------------------
; AX = integer
putint:
        pusha
        mov bx, 10
        xor cx, cx
.L0:    xor dx, dx
        div bx
        push dx
        inc cx
        cmp ax, 0
        jnz .L0
.L1:    pop ax
        add al, 30h
        call putc
        loop .L1
        popa
        ret

;--------------------------------
; SI = buffer
gets:
        pusha
        mov dx, si
        mov ah, 0Ah
        int 21h
        xor bh, bh
        mov bl, [si+1]
        mov byte [bx+si+2], 0
        popa
        ret

;--------------------------------
; in: SI = string
; out: AX = integer value
atoi:
        push cx bx dx si di
        xor di, di
        mov al, [si]
        cmp al, '-'
        jnz .L1
        mov di, 1
        inc si
.L1:    xor ax, ax
        xor bx, bx
        mov cx, 10
.L2:    mov bl, [si]
        cmp bl, 0
        jz .L3
        mul cx
        sub bl, 30h
        add ax, bx
        inc si
        jmp .L2
.L3:    cmp di, 0
        jz .L0
        neg ax
.L0:    pop di si dx bx cx
        ret
       

Ένα παράδειγμα χρήσης.

Κώδικας: Επιλογή όλων

        org 100h

        mov ax, 3               ; text mode
        int 10h

        mov ax, 80              ; print 80
        call putint             ;

        call newline
        mov ax, -80             ; print -80
        call putsint            ;

        call newline
        mov ax, 0FFFFh          ; print 65535
        call putint             ;

        call newline
        mov ax, 0FFFFh          ; print -1
        call putsint            ;

        call newline
        mov si, msg1            ; print msg1
        call puts               ;
        mov si, buff            ; input buffer
        call gets               ;

        call newline
        mov si, buff+2          ; print buffer
        call puts               ;
        mov si, msg2            ; print msg2
        call puts               ;
        mov si, buff            ; input buffer
        call gets               ;

        call newline
        mov si, buff+2          ; print buffer
        call puts               ;
        mov si, msg3            ; print msg3
        call puts               ;

        mov si, buff+2          ; string to binary
        call atoi               ;
        add ax, 1000
        call putsint            ; print number
        call newline

        xor ah, ah
        int 16h
        ret

        msg1 db "Enter your name: ",0
        msg2 db " enter a number: ",0
        msg3 db " + 1000 = ",0         
        
        buff db 80h,0,80h dup (?) 
Καλή διασκέδαση.

nkast
Δημοσιεύσεις: 137
Εγγραφή: 15 Νοέμ 2009 20:31
Επικοινωνία:

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από nkast » 08 Δεκ 2011 02:16

LightForce έγραψε:nkast υπόψην δεν μπορείς απευθείας να 'σπρώξεις' 8 bit καταχωρητή στην στοίβα σε intel αρχιτεκτονική. To νόημα όπως φαίνεται :)

Κώδικας: Επιλογή όλων

 push AL 
duh! Εχεις δίκιο.

Το σκεπτικο ειναι πως μπορεις να σπρωχνεις στην στοίβα χαρακτηρες μεχρι να λαβεις το enter.
Στη συνέχεια μπορεις να τους διαβαζεις εναν εναν, μετατροπή σε int και πολλαπλασιασμός επι 10. Μετα καταλαβα οτι μπορεις να κανεις το ιδιο χωρις στοίβα!

Απλα στην πρωτη περιπτωση ελενχεις στο τελος την βαση της στoιβας για '-' και κανεις comp'2.
Στη δευτερη , κρατας στην αρχη σε ενα καταχωριτη μια τιμη για το αν πατησε το '-' και στο τελος ελενχεις την τιμη του καταχωρητη για να κανεις comp'2.


Η ίδια πρακτική μπορεί να φανει χρήσιμη για την μετατροπή του αριθμου σε ascii και άμεση εκτύπωση του. Χωρίς να δεσμεύσεις πίνακα, απλα δουλεύοντας πάνω στο stack.

kkkkonstantina
Δημοσιεύσεις: 14
Εγγραφή: 12 Νοέμ 2009 17:49

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από kkkkonstantina » 08 Δεκ 2011 10:55

Ένωσα κάποια κομμάτια από τις ρουτίνες που μου έδωσες και τα έβαλα μέσα στο πρόγραμμα μου και το έτρεξα απλά δεν ξέρω για ποιο λόγο ενώ ο πίνακας είναι 10 θέσεων δεν σταματάει μόλις πληκτρολογήσω και τους 10 αριθμούς ενώ του ορίζω το μέγεθος!
Άν έχεις όρεξη ρίξε μια ματιά !Θα λείψω κάποιες μέρες οπότε μετά θα επιστρέψω με περισσότερη όρεξη για δουλεία :-)

Κώδικας: Επιλογή όλων


format MZ
push cs
pop ds

mov SI,pinakasA


mov AH,09 ;emfanisi mhnumatos
mov DX,inmsg
int 21h

mov CX,10 ;poses fores 8a ektele8ei o brogxos

gem: ;gemisma pinaka

mov AH,1
int 21h

mov DL, AL ;metatroph ari8mou se kwdika ascii
sub DL, 30h
mov [SI],DL



putsint: 
        cmp ax, 0 
        jns .L1 
        push ax 
        mov al, '-' 
        call putc 
        pop ax 
        neg ax 
.L1:    call putint 
        ret 


inc SI

loop gem

mov AH,09 ;emfanisi kenou xarakthra
mov DX,keno
int 21h



mov CX,10

mov SI,pinakasA

emfanisi:

mov AX,0
mov AL,[SI]
mov DX,AX
mov DI,X
add DI,2

L2:

mov AX,DX
mov DX,0
mov BX,10
div BX

xchg AX,DX
add AL,30H
mov [DI],AL

dec DI
cmp DX,0
jnz L2

mov AH,09
mov DX,X
int 21h

mov AH,09
mov DX,keno
int 21h

inc SI
mov DI,0



loop emfanisi


exit:
mov AX,4C00h
int 21h



inmsg db 'dwse 10 arithmous gia ton pinaka: ','$'
keno db 0Ah,0Dh,'$'
pinakasA db ?,?,?,?,?,?,?,?,?,?
X db 30h,30h,30h,'$'

LightForce
WebDev Moderator
Δημοσιεύσεις: 3812
Εγγραφή: 13 Απρ 2003 23:49

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από LightForce » 09 Δεκ 2011 12:14

nkast έγραψε: Στη δευτερη , κρατας στην αρχη σε ενα καταχωριτη μια τιμη για το αν πατησε το '-' και στο τελος ελενχεις την τιμη του καταχωρητη για να κανεις comp'2.
Έτσι δουλεύει και η atoi που έκανα ποστ, 0 η 1 στον di και στο τέλος συμπλήρωμα ως προς 2 εάν υπήρξε πρόσημο.


kkkkonstantina στο σημείο που τοποθέτησες την putsint δεν έχει αποτέλεσμα.
Πειραματίσου περισσότερο με τις ρουτίνες πριν τις καλέσεις από τον κώδικα σου.

nkast
Δημοσιεύσεις: 137
Εγγραφή: 15 Νοέμ 2009 20:31
Επικοινωνία:

Ερώτηση για αρνητικούς αριθμούς

Δημοσίευση από nkast » 10 Δεκ 2011 23:46

LightForce έγραψε:
nkast έγραψε: Στη δευτερη , κρατας στην αρχη σε ενα καταχωριτη μια τιμη για το αν πατησε το '-' και στο τελος ελενχεις την τιμη του καταχωρητη για να κανεις comp'2.
Έτσι δουλεύει και η atoi που έκανα ποστ, 0 η 1 στον di και στο τέλος συμπλήρωμα ως προς 2 εάν υπήρξε πρόσημο.

Δεν το ειχα δει.
Καταπληκτική δουλειά!

Απάντηση

Επιστροφή στο “Assembly”

Μέλη σε σύνδεση

Μέλη σε αυτήν τη Δ. Συζήτηση: Δεν υπάρχουν εγγεγραμμένα μέλη και 0 επισκέπτες