tutorials.de Buch-Aktion 05/2012
ERLEDIGT
NEIN
ANTWORTEN
14
ZUGRIFFE
1017
EMPFEHLEN
  • An Twitter übertragen
  • An Facebook übertragen
AUF DIESES THEMA
ANTWORTEN
  1. #1
    Avatar von polar
    polar polar ist offline Mitglied Silber
    Registriert seit
    Aug 2002
    Beiträge
    97
    hi! habe folgendes prob:

    ich schreibe daten (meistens zahlen bis 255) byteweise in eine datei. leider habe ich das problem, das ich eine zahl habe, die größer ist als 255. wenn ich diese zahl als integer in die datei schreibe, bekomme ich einen total falschen wert. wie kann ich den integer in zwei bytes aufteilen**** also erst die eine hälfte des int's schreiben, dann die andere.. **** geht das ****

    danke im vorraus
     

  2. #2
    Registriert seit
    Nov 2001
    Ort
    Gießen
    Beiträge
    4.091
    ich hab zwar keine besonders elegante lösung dafür, aber immerhin funktioniert es. du musst erstmal deine zahl ins binärsystem übertragen:
    Code :
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    
    Dim i As Integer
    Dim b As String
     
    i = 777
    Do While i > 0
        If i Mod 2 <> 0 Then
            b = "1" & b
        Else
            b = "0" & b
        End If
        i = i \ 2
    Loop
     
    MsgBox b

    von jetzt an bieten sich dir zwei möglichkeiten. entweder du speicherst die binären werte als text - aber das ist zugegebenermassen keine besonders tolle lösung. oder du nimmst dir daraus einfach deine beiden byte-werte:
    wenn der string mit dem binärwert der zahl dann länger als 8 zeichen ist, legst du einfach die letzten 8 zeichen in variable x und die restlichen zeichen in variable y ab. in dem beispiel wäre variable x = "00001001" und y = "11".

    dann erzeugst du aus deinen beiden binärwerten wieder zwei "richtige" zahlen:
    Code :
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    
    Dim b As String
    Dim i As Integer
    Dim c As Integer 'zählervariable
     
    b = "1001"
    For c = 1 To Len(b)
        i = i + CInt(Mid(b, c, 1) * 2 ^ (c - 1))
    Next c
     
    MsgBox CStr(i)

    und schon hast du zwei ganze zahlen, die beide in eine byte-variable passen. wenn du dazu noch fragen hast, meld dich nochmal.
     
    "You could say that I was too lazy to calculate and so I invented the computer." -- Konrad Zuse

  3. #3
    Avatar von polar
    polar polar ist offline Mitglied Silber
    Registriert seit
    Aug 2002
    Beiträge
    97
    das hilft mir schon weiter.
    vielen dank für die mühe!
     

  4. #4
    Registriert seit
    Nov 2001
    Ort
    Gießen
    Beiträge
    4.091
    es wäre natürlich auch praktisch, das später wieder zurück zu rechnen. um nochmal die werte aus dem beispiel zu benutzen:
    11 = 3
    00001001 = 9

    Code :
    1
    2
    
    ergebnis binär  : 11 + (11 * 11111111) + 00001001 = 1100001001
    ergebnis dezimal:  3 + ( 3 *      255) +        9 =        777
     
    "You could say that I was too lazy to calculate and so I invented the computer." -- Konrad Zuse

  5. #5
    Avatar von Crayzee Ivan
    Crayzee Ivan Crayzee Ivan ist offline Mitglied Bronze
    Registriert seit
    Jul 2002
    Beiträge
    40
    Ich hätte da noch ne andere Möglichkeit anzubieten.

    Zum "zerteilen" in erstes und zweites Byte:
    Code :
    1
    2
    3
    4
    5
    6
    7
    
    Dim high as byte, low as byte
     
    'X ist das Integer
    'erstes Byte
    high = (X And &HFF00) - &HFF
    'zweites Byte
    low = X And &HFF
    Das ergibt zB für 312 high = 1 und low = 56. Die beiden Zahlen einfach in die Datei schreiben.

    Beim Einlesen wird wieder "zusammengesetzt":
    Code :
    1
    2
    3
    
    '... high und low werden eingelesen
     
    X = (high + &HFF) Or low
    Für high = 1 und low = 56 ergibt das wieder 312.

    Zur Erklärung: 312 ist binär 1|00111000, was mehr als 8Bit, also ein Byte ist (Markiert durch senkrechten Strich). Mit der oben vorgestellten Methode trennt man den Teil, der im ersten Byte liegt - also 1 - von dem im zweiten Byte - also 111000 (56).

    -Crayzee Ivan
     

  6. #6
    Registriert seit
    Nov 2001
    Ort
    Gießen
    Beiträge
    4.091
    die möglichkeit ist zwar wesentlich kürzer, und auch vom ansatz her besser gedacht als meine - allerdings funktioniert das nur mit zahlen kleiner als 512, bei allen darüber gibt es einen speicherüberlauf.

    meine variante war auch eher auf den rechnerischen weg ausgearbeitet und wie gesagt nicht unbedingt das absolute nonplusultra - aber es funktioniert (mehr oder weniger jedenfalls ).
    noch eine möglichkeit wäre bitweises verschieben, was ja der multiplikation/division mit 2 entspricht.
     
    "You could say that I was too lazy to calculate and so I invented the computer." -- Konrad Zuse

  7. #7
    Avatar von polar
    polar polar ist offline Mitglied Silber
    Registriert seit
    Aug 2002
    Beiträge
    97
    vielecht gehts auch noch anders, ich spezifizier nochmal:

    also meine variablen sind alle vom type byte. die zahlen die ich mit "Put" in die binär geöffnete datei schreibe liegen alle im bereich 0 - 255, also kein problem. strings schreibe ich zeichenweise in die datei, auch kein problem. allerdings habe ich eben noch eine variable die, die anzahl der gesamten daten beinhaltet. die kann eigentlich 0 - unendlich groß sein. dürfte aber nich über 60.000 gehen =) also ist ein integer ausreichend. wenn ich jetzt den int mit "Put" in die datei schreibe sieht es für mich so aus als würde er nur ein byte schreiben. aber laut der hilfe, sollte das trotzdem ****en. "Print" geht auch nicht und "Write" kann ich eh vergessen.

    warum kann ich mit "Put" den integer nicht korrekt schreiben****?

    asphyxia: ich probier gleich mal deine methode aus.

    danke nochmal
     

  8. #8
    Avatar von polar
    polar polar ist offline Mitglied Silber
    Registriert seit
    Aug 2002
    Beiträge
    97
    asphyxia: mit deiner methode bekomm ich das nicht ganz hin. wenn ich meiner funktion folgenden string übergebe "393" bekomme ich als einzelne werte nur "0" und "3" zurück. ich poste mal den code...

    mein type:

    PHP-Code:
    Type Word

         Lower 
    As Byte
         Upper 
    As Byte
         
    End Type 
    meine funktion:

    PHP-Code:
    Private Function IntSpalter(doomedVar As String)
    Dim by As String
    Dim by1 
    As String
    Dim by2 
    As String
    Dim i 
    As Integer
    Dim Data_Word 
    As Word

    Len(doomedVar)
        
        Do While 
    0
            
    If i Mod 2 <> 0 Then
                by 
    "1" by
            
    Else
                
    by "0" by
            End 
    If
            
    2
        Loop
        
    If Len(by) > 8 Then
        by1 
    Mid(by18)
        
        For 
    1 To Len(by1)
            
    Data_Word.Lower Data_Word.Lower CInt(Mid(by1i1) * ^ (1))
        
    Next i
        
        by2 
    Mid(by9Len(doomedVar))
        
        For 
    1 To Len(by2)
            
    Data_Word.Upper Data_Word.Upper CInt(Mid(by2i1) * ^ (1))
        
    Next i
        
    Else
        
    Data_Word.Lower 0
        
        
    For 1 To Len(by)
            
    Data_Word.Upper Data_Word.Upper CInt(Mid(byi1) * ^ (1))
        
    Next i
        
    End 
    If

    'IntSpalter (Data_Word)
    MsgBox CStr(Data_Word.Lower)
    MsgBox CStr(Data_Word.Upper)
    End Function 
    hoffe das schafft etwas klarheit

    edit: mit den PHP tags klappt die darstellung nicht so ganz.
    End Type und End Function fehlt irgendwie *g*
    Geändert von polar (30.10.02 um 11:44 Uhr)
     

  9. #9
    Avatar von Crayzee Ivan
    Crayzee Ivan Crayzee Ivan ist offline Mitglied Bronze
    Registriert seit
    Jul 2002
    Beiträge
    40
    @asphyxia: Mist . Das war eigentlich nur ne alte Funktion, aber offensichtlich hab ich der nie Zahlen übergeben, die größer als 511 waren . Als beste Lösung bleibt dann wohl nur noch das Byte-Shiften, aber da weiß ich jetzt nicht genau, wie man das in VB realisieren könnte.

    @polar: Ich habe ein paar Fehler in deiner Funktion gefunden und korrigiert, folgendes sollte funktionieren:
    Code :
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    
    Private Function IntSpalter(doomedVar As String)
    Dim by As String
    Dim by1 As String
    Dim by2 As String
    Dim i As Integer
    Dim Data_Word As Word
     
    i = Val(doomedVar)
    'gesucht war der Zahlenwert, nicht die Länge, also Val statt Len
        
        Do While i > 0
            If i Mod 2 <> 0 Then
                by = "1" & by
            Else
                by = "0" & by
            End If
            i = i \ 2
        Loop
        
    If Len(by) > 8 Then
        by1 = Right$(by, 8)
        
        For i = 1 To 8
            Data_Word.Lower = Data_Word.Lower + CInt(Mid(by1, (8 + 1) - i, 1) * 2 ^ (i - 1))
            'Die Strings wurden falsch rum ausgelesen, die abarbeitung
            'der Binärzahlen muss von hinten anfangen. Das fiel bei 
            'asphyxias Beispiel nicht auf, weil "1001" von hinten und 
            'vorne das selbe ist.
        Next i
        
        by2 = Left$(by, Len(by) - 8)
        
        For i = 1 To Len(by2)
            Data_Word.Upper = Data_Word.Upper + CInt(Mid(by2, (Len(by2) + 1) - i, 1) * 2 ^ (i - 1))
        Next i
        
    Else
        Data_Word.Lower = 0
        
        For i = 1 To Len(by)
            Data_Word.Upper = Data_Word.Upper + CInt(Mid(by, (Len(by) + 1) - i, 1) * 2 ^ (i - 1))
        Next i
        
    End If
     
    'IntSpalter (Data_Word)
    MsgBox CStr(Data_Word.Lower)
    MsgBox CStr(Data_Word.Upper)
    End Function

    -Crayzee Ivan
    Geändert von Crayzee Ivan (30.10.02 um 12:42 Uhr)
     

  10. #10
    Avatar von polar
    polar polar ist offline Mitglied Silber
    Registriert seit
    Aug 2002
    Beiträge
    97
    danke für deine korrektur ivan

    wenn ich jetzt by1 und by2 mit der MsgBox zum testen ausgeben lasse, bekomme ich folgende werte: "137" und anschliessend "1" *fg* klappt doch nicht so ganz.
     

  11. #11
    Registriert seit
    Nov 2001
    Ort
    Gießen
    Beiträge
    4.091
    folgende werte: "137" und anschliessend "1" *fg* klappt doch nicht so ganz.
    stimmt doch: 1 + (1 * 255) + 137 = 393.
     
    "You could say that I was too lazy to calculate and so I invented the computer." -- Konrad Zuse

  12. #12
    Avatar von polar
    polar polar ist offline Mitglied Silber
    Registriert seit
    Aug 2002
    Beiträge
    97
    ja aber wenn ich das jetzt in meine binäre datei schreibe bekomme ich trotzdem einen falschen wert. hmm aber danke für's vorrechnen *g*
     

  13. #13
    Registriert seit
    Nov 2001
    Ort
    Gießen
    Beiträge
    4.091
    welchen wert kriegst du denn, wenn du die beiden byte-werte in die datei schreibst - oder anders gefragt: was heisst "falscher wert"?
     
    "You could say that I was too lazy to calculate and so I invented the computer." -- Konrad Zuse

  14. #14
    Avatar von polar
    polar polar ist offline Mitglied Silber
    Registriert seit
    Aug 2002
    Beiträge
    97
    folgenden hex wert bekomme ich: 8901 wenn ich mir die datei dann mit meinem hex edi anschaue. das entspricht dem wert 137 *g*

    die anzahl der datensätze, für diese datei ist aber: 393.

    irgendwo steckt noch ein fehler.. *grübel*

    innerhalb meiner funktion intSpalter, schreibe ich mein type direkt mit put in die datei:

    : : :

    Put #1, , Data_Word

    End Function

    edit: mach ich das mit 1795 datensätzen, steht 219 in meiner datei.
    edit2: *g* was ich allerdings immer noch nicht verstehe, warum kann ich zb. 1795 mit put nicht korrekt in die datei ausgeben. kann mir das mal jemand erklären**** schreibt put nur bytes?
    Geändert von polar (30.10.02 um 15:09 Uhr)
     

  15. #15
    Avatar von polar
    polar polar ist offline Mitglied Silber
    Registriert seit
    Aug 2002
    Beiträge
    97
    so sorry für den stress habe big und little vertauscht. wenn ich 393 jetzt schreibe entspricht das 0189 (vorher 8901). auf jeden fall passt es jetzt. danke
     

Ähnliche Themen

  1. Konvertierung von Integer in Byte Array
    Von javaprogger1987 im Forum Java
    Antworten: 14
    Letzter Beitrag: 05.01.10, 21:09
  2. Integer aus byte[] ohne ByteArrayInputStream
    Von procurve im Forum Java Grundlagen
    Antworten: 4
    Letzter Beitrag: 17.02.09, 14:59
  3. Antworten: 4
    Letzter Beitrag: 19.04.07, 15:15
  4. byte udn integer
    Von MinaM im Forum Java
    Antworten: 2
    Letzter Beitrag: 12.07.05, 13:11
  5. Integer to Byte
    Von Wolfsbein im Forum Java
    Antworten: 5
    Letzter Beitrag: 18.10.04, 13:17