У меня есть база данных DBase IV. В каждой строке есть памятное поле со строкой в кодировке ASCII, которая содержит две сериализованные структуры borland c ++. Я могу извлечь данные с помощью OleDb, перекодировать их в ascii с помощью класса ASCIIEncoding, преобразовать их в байты с помощью BinaryReader и преобразовать их в мою структуру C # с помощью Marshal.PtrToStructure. Данные, которые я получаю, верны, но любое значение с плавающей запятой, которое слишком велико в базе данных, совершенно неверно, когда оно приводится к c #. Например, значение 1149.00 приведено к 764.9844, но значение как 64.00 приведено к штрафу. Я могу опубликовать часть кода и структур, но я решил, что сначала я старался сделать его коротким. Я знаю, что значения с плавающей точкой имеют точность до 7 цифр, но я не понимаю, почему я вижу это, потому что значения ниже этого предела.
Edit:
struct cplusplusstruct // from the c++ code
{
int Number;
float P;
float ZP;
float Hours;
int Month;
int Day;
int Year;
int Hour;
int Minute;
int Second;
ULONG UPCTime;
int B;
char Name[21];
float L;
float H;
float S;
}
[StructLayout(LayoutKind.Sequential, Pack = 1)]
public struct csharpstruct //The C# struct I created
{
public int Number;
public float Pr;
public float ZP;
public float Hours;
public int Month;
public int Day;
public int Year;
public int Hour;
public int Minute;
public int Second;
public UInt32 UPCTime;
public int B;
[MarshalAsAttribute(UnmanagedType.ByValTStr, SizeConst = 21)]
public string Name;
public float L;
public float H;
public float S;
}
//OLE DB Connection and query ...
//Casting data to struct
ASCIIEncoding encoding = new ASCIIEncoding();
byte[] blob = encoding.GetBytes(memoString);
MemoryStream memoryStream = new MemoryStream(blob);
BinaryReader binaryReader = new BinaryReader(memoryStream);
int dataSize = Marshal.SizeOf(typeof(csharpstruct));
GCHandle handle = GCHandle.Alloc(binaryReader.ReadBytes(dataSize), GCHandleType.Pinned);
csharpstruct data = (csharpstruct) Marshal.PtrToStructure(handle.AddrOfPinnedObject(), typeof(csharpstruct));
Редактировать: Ниже приведен код Java, который отлично читает данные, но без использования приведения.
org.xBaseJ.DBF dbf = new org.xBaseJ.DBF(dbPath);
org.xBaseJ.DBF dbf = new org.xBaseJ.DBF(dbPath);
MemoField m = (MemoField) dbf.getField("MEMOFIELD");
Charset charset = Charset.forName("US-ASCII");
CharsetDecoder decoder = charset.newDecoder();
ByteBuffer trendBytes = ByteBuffer.wrap(m.getBytes());
trendBytes.order(ByteOrder.LITTLE_ENDIAN);
trendBytes.getInt();
trendBytes.getFloat();