Differenze tra le versioni di "Ottenere un numero dalla sua memorizzazione in formato Big-Endian"

Da Gambas-it.org - Wikipedia.
Riga 1: Riga 1:
Il caso è quello in cui si intende convertire i dati di un valore, memorizzati in formato Big-Endian a dimensione fissa all'interno di un file o di un vettore di tipo Byte[], ottenendo così al termine l'effettivo numero corrispondente (ossia corrispondente esattamente alla disposizione dei byte in formato ''big-endian'').
+
La circostanza è quella in cui si intende leggere i dati-byte di un valore all'interno di un file memorizzati in formato ''Big-Endian'' a dimensione fissa, ottenendo così al termine l'effettivo numero corrispondente (ossia corrispondente esattamente alla disposizione dei dati-byte in formato ''Big-Endian'').
  
 +
Come sappiamo, se un valore è stato volutamente salvato in modalità ''Big-Endian'' all'interno di un file, andando successivamente a leggerlo, il sistema, che  certamente opera con una modalità di memorizzazione dei dati in ''Little-Endian'', non restituirà dalla lettura il valore esatto.
 +
<BR>Così, ad esempio, se nel file è memorizzato il gruppo di tre byte-dati &h010305, corrispondente in rappresentazione decimale al numero 66309, una lettura in ''Little-Endian'' ruoterà i dati-byte di quel valore, come segue: &h050301, ordine di byte che corrisponde invece al numero 328449 !
  
===Caso di memorizzazione in un vettore di tipo Byte[]===
 
Porremo come esempio un vettore di tipo Byte[] di quattro elementi, contenente i seguenti valori: &01, &02, &03 e &04. Per ottenere il corrispondente numero decimale - che è ''16909060'' - potremo utilizzare alcune modalità:
 
  
 +
Mostriamo alcune possibiità, con le quali poter restituire, dalla lettura da un file di suoi 3 dati memorizzati in ''Big-Endian'', l'effettivo valore che si volle a suo tempo memorizzare nel file.
 
  '''Public''' Sub Main()
 
  '''Public''' Sub Main()
 
   
 
   
   Dim bb As Byte[] = [&01, &02, &03, &04]
+
  Dim fl As File
 +
  Dim b, c As Byte
 +
  Dim i As Integer
 +
 
 +
  fl = Open "<FONT Color=gray>''/percorso/del/file''</font>" For Read
 +
 
 +
<FONT Color=gray>' ''Leggerà tre byte:''</font>
 +
  b = 3
 +
 
 +
  Do
 +
    Read #fl, c
 +
    i = Shl(i, 8) Or c
 +
    Dec b
 +
  Loop Until b = 0
 +
 
 +
  Print i
 +
 
 +
'''End'''
 +
 
 +
 
 +
====Usando un vettore di tipo Byte[] come appoggio====
 +
'''Public''' Sub Main()
 +
 +
  Dim fl As File
 +
   Dim bb As Byte[]
 +
  Dim i As Integer
 +
 
 +
  fl = Open "<FONT Color=gray>''/percorso/del/file''</font>" For Read
 +
 
 +
<FONT Color=gray>' ''Legge i tre byte:''</font>
 +
  With bb = New Byte[3]
 +
    .Read(fl, 0, bb.Count)
 +
    .Reverse()
 +
  End With
 +
   
 +
  i = Int@(bb.Data)
 +
 
 +
  Print i
 +
 
 +
'''End'''
 +
oppure:
 +
'''Public''' Sub Main()
 +
 +
  Dim fl As File
 +
  Dim bb As New Byte[3]
 
   Dim i As Integer
 
   Dim i As Integer
 
    
 
    
 +
  fl = Open "<FONT Color=gray>''/percorso/del/file''</font>" For Read
 +
 
 +
  bb.Read(fl, 0, bb.Count)
 +
 
 +
  fl.Close
 +
 
 
   i = bb[0]
 
   i = bb[0]
 
   i = i * CInt(2 ^ 8)
 
   i = i * CInt(2 ^ 8)
Riga 15: Riga 66:
 
   i = i * CInt(2 ^ 8)
 
   i = i * CInt(2 ^ 8)
 
   i = i Or (bb[2] And 127)
 
   i = i Or (bb[2] And 127)
  i = i * CInt(2 ^ 8)
 
  i = i Or (bb[3] And 127)
 
 
      
 
      
 
   Print i
 
   Print i
Riga 25: Riga 74:
 
oppure:
 
oppure:
 
  '''Public''' Sub Main()
 
  '''Public''' Sub Main()
+
 
 +
  Dim fl As File
 
   Dim q As Byte
 
   Dim q As Byte
   Dim bb As Byte[] = [&01, &02, &03, &04]
+
   Dim bb As New Byte[3]
 
   Dim ris As Integer
 
   Dim ris As Integer
     
+
 
 +
  fl = Open "<FONT Color=gray>''/percorso/del/file''</font>" For Read
 +
 
 +
  bb.Read(fl, 0, bb.Count)
 +
 
 +
  fl.Close
 +
 
 
   Do
 
   Do
 
     ris = (ris * CInt(2 ^ 8)) Or bb[q]
 
     ris = (ris * CInt(2 ^ 8)) Or bb[q]
Riga 43: Riga 99:
 
  '''Public''' Sub Main()
 
  '''Public''' Sub Main()
 
   
 
   
   Dim bb As Byte[] = [&01, &02, &03, &04]
+
  Dim fl As File
 +
   Dim bb As New Byte[3]
 
   Dim i As Integer
 
   Dim i As Integer
 +
 
 +
  fl = Open "<FONT Color=gray>''/percorso/del/file''</font>" For Read
 +
 
 +
  bb.Read(fl, 0, bb.Count)
 +
 
 +
  fl.Close
 
   
 
   
   i = bb[3]
+
   i = bb[2]
   i += bb[2] * 256            <FONT Color=gray>' ''&0100''</font>
+
   i += bb[1] * 256            <FONT Color=gray>' ''&0100''</font>
   i += bb[1] * 65536        <FONT Color=gray>' ''&010000''</font>
+
   i += bb[0] * 65536        <FONT Color=gray>' ''&010000''</font>
   i += bb[0] * 16777216  <FONT Color=gray>' ''&01000000''</font>
+
    
 
 
   Print i
 
   Print i
+
 
 
  '''End'''
 
  '''End'''
  
Riga 59: Riga 121:
 
  '''Public''' Sub Main()
 
  '''Public''' Sub Main()
 
    
 
    
   Dim bb As Byte[] = [&01, &02, &03, &04]
+
  Dim fl As File
 +
   Dim bb As New Byte[3]
 
   Dim i As Integer
 
   Dim i As Integer
 +
 
 +
  fl = Open "<FONT Color=gray>''/percorso/del/file''</font>" For Read
 +
 
 +
  bb.Read(fl, 0, bb.Count)
 +
 
 +
  fl.Close
 
    
 
    
   i = (bb[3] Or ((bb[2] * CInt(2 ^ 8)))) Or (bb[1] * CInt(2 ^ 16)) Or (bb[0] * CInt(2 ^ 24))
+
   i = bb[2] Or Shl(bb[1], 8) Or Shl(bb[0], 16)
 
      
 
      
 
   Print i
 
   Print i
Riga 69: Riga 138:
  
  
o usando le risorse ''Stringa'' con conversione finale in valore numerico in rappresentazione decimale:
+
o usando le risorse ''stringa'' con conversione finale in valore numerico in rappresentazione decimale:
 
  '''Public''' Sub Main()
 
  '''Public''' Sub Main()
 
   
 
   
   Dim bb As Byte[] = [&01, &02, &03, &04]
+
  Dim fl As File
 +
   Dim bb As New Byte[3]
 
   Dim s As String
 
   Dim s As String
 
   Dim i As Integer
 
   Dim i As Integer
 
 
  s = Hex(bb[0], 2) & Hex(bb[1], 2) & Hex(bb[2], 2) & Hex(bb[3], 2)
 
 
    
 
    
  i = Val("&" & s)
 
   
 
  Print i
 
 
 
'''End'''
 
 
 
====Esempi usando la lettura dei dati da un file====
 
Mostriamo ora due esempi di lettura da un file dei suoi dati memorizzati in ''Big-Endian''. Va precisato che le due modalità appresso mostrate possono essere utilizzate ovviamente anche per convertire valori presenti - come sopra - in vettori di tipo ''Byte[ ]''.
 
'''Public''' Sub Main()
 
 
  Dim fl As File
 
  Dim bb As Byte[]
 
  Dim i As Integer
 
 
 
 
   fl = Open "<FONT Color=gray>''/percorso/del/file''</font>" For Read
 
   fl = Open "<FONT Color=gray>''/percorso/del/file''</font>" For Read
 
    
 
    
<FONT Color=gray>' ''Legge ad esempio 32 bit (4 byte):''</font>
+
   bb.Read(fl, 0, bb.Count)
   With bb = New Byte[4]
 
    .Read(fl, 0, 4)
 
    .Reverse()
 
  End With
 
   
 
  i = Int@(bb.Data)
 
 
    
 
    
   Print i
+
   fl.Close
 
    
 
    
'''End'''
+
  s = Hex(bb[0], 2) & Hex(bb[1], 2) & Hex(bb[2], 2) & Hex(bb[3], 2)
oppure:
 
'''Public''' Sub Main()
 
 
  Dim fl As File
 
  Dim b, c As Byte
 
  Dim j As Integer
 
 
 
  fl = Open "<FONT Color=gray>''/percorso/del/file''</font>" For Read
 
 
    
 
    
<FONT Color=gray>' ''Legge ad esempio 32 bit (4 byte):''</font>
+
   i = Val("&" & s)
  b = 4
+
   
 
+
   Print i
   Do
 
    Read #fl, c
 
    j = Shl(j, 8) Or c
 
    Dec b
 
   Loop Until b = 0
 
 
    
 
    
  Print j
 
 
 
 
  '''End'''
 
  '''End'''
Laddove in questa seconda modalità:
 
* "''fl''" è la variabile del file contenente i byte del numero disposti in ''Big-Endian'';
 
* "''b''" è la variabile contenente la quantità (2, 4 oppure 8) di byte, disposti in ''Big-Endian'', che costituiscono il numero e quindi che devono essere letti;
 
* "''c''" è la variabile che contiene il valore del singolo byte letto dal file;
 
* "''j''" è la variabile contenente il risultato.
 

Versione delle 02:25, 17 apr 2018

La circostanza è quella in cui si intende leggere i dati-byte di un valore all'interno di un file memorizzati in formato Big-Endian a dimensione fissa, ottenendo così al termine l'effettivo numero corrispondente (ossia corrispondente esattamente alla disposizione dei dati-byte in formato Big-Endian).

Come sappiamo, se un valore è stato volutamente salvato in modalità Big-Endian all'interno di un file, andando successivamente a leggerlo, il sistema, che certamente opera con una modalità di memorizzazione dei dati in Little-Endian, non restituirà dalla lettura il valore esatto.
Così, ad esempio, se nel file è memorizzato il gruppo di tre byte-dati &h010305, corrispondente in rappresentazione decimale al numero 66309, una lettura in Little-Endian ruoterà i dati-byte di quel valore, come segue: &h050301, ordine di byte che corrisponde invece al numero 328449 !


Mostriamo alcune possibiità, con le quali poter restituire, dalla lettura da un file di suoi 3 dati memorizzati in Big-Endian, l'effettivo valore che si volle a suo tempo memorizzare nel file.

Public Sub Main()

 Dim fl As File
 Dim b, c As Byte 
 Dim i As Integer
 
  fl = Open "/percorso/del/file" For Read
  
' Leggerà tre byte:
  b = 3
  
  Do
    Read #fl, c
    i = Shl(i, 8) Or c
    Dec b
  Loop Until b = 0
  
  Print i
 
End


Usando un vettore di tipo Byte[] come appoggio

Public Sub Main()

 Dim fl As File
 Dim bb As Byte[]
 Dim i As Integer
 
  fl = Open "/percorso/del/file" For Read
  
' Legge i tre byte:
  With bb = New Byte[3]
    .Read(fl, 0, bb.Count)
    .Reverse()
  End With
   
  i = Int@(bb.Data)
  
  Print i
  
End

oppure:

Public Sub Main()

 Dim fl As File
 Dim bb As New Byte[3]
 Dim i As Integer
 
  fl = Open "/percorso/del/file" For Read
  
  bb.Read(fl, 0, bb.Count)
  
  fl.Close
  
  i = bb[0]
  i = i * CInt(2 ^ 8)
  i = i Or (bb[1] And 127)
  i = i * CInt(2 ^ 8)
  i = i Or (bb[2] And 127)
   
  Print i
 
End


oppure:

Public Sub Main()
 
 Dim fl As File
 Dim q As Byte
 Dim bb As New Byte[3]
 Dim ris As Integer
  
  fl = Open "/percorso/del/file" For Read
  
  bb.Read(fl, 0, bb.Count)
  
  fl.Close
  
  Do
    ris = (ris * CInt(2 ^ 8)) Or bb[q]
    Inc q
  Loop Until q = bb.Count

  Print ris

End


oppure:

Public Sub Main()

 Dim fl As File
 Dim bb As New Byte[3]
 Dim i As Integer
 
  fl = Open "/percorso/del/file" For Read
  
  bb.Read(fl, 0, bb.Count)
  
  fl.Close

  i = bb[2]
  i += bb[1] * 256            ' &0100
  i += bb[0] * 65536        ' &010000
  
  Print i
  
End


oppure:

Public Sub Main()
 
 Dim fl As File
 Dim bb As New Byte[3]
 Dim i As Integer
  
  fl = Open "/percorso/del/file" For Read
  
  bb.Read(fl, 0, bb.Count)
  
  fl.Close
 
  i = bb[2] Or Shl(bb[1], 8) Or Shl(bb[0], 16)
   
  Print i
  
End


o usando le risorse stringa con conversione finale in valore numerico in rappresentazione decimale:

Public Sub Main()

 Dim fl As File
 Dim bb As New Byte[3]
 Dim s As String
 Dim i As Integer
  
  fl = Open "/percorso/del/file" For Read
  
  bb.Read(fl, 0, bb.Count)
  
  fl.Close
  
  s = Hex(bb[0], 2) & Hex(bb[1], 2) & Hex(bb[2], 2) & Hex(bb[3], 2)
  
  i = Val("&" & s)
   
  Print i
  
End