.NET을 사용하여 FoxPro 메모 필드에서 데이터를 추출하려면 어떻게합니까?

StackOverflow https://stackoverflow.com/questions/428237

문제

FoxPro 데이터베이스를 XML로 변환하기 위해 C# 프로그램을 작성하고 있으며 메모 필드를 제외한 모든 것이 비어 있습니다. 내가 그 비트를 변환하기 위해 놓친 것이 있습니까?

C# .NET 3.5 SP1, Visual FoxPro 9 SP 1 Ole DB 드라이버를 사용하고 있습니다. 다른 모든 데이터가 제대로 가져 오면 연결 문자열은 괜찮습니다.

FoxPro 데이터베이스를 SQL Server로 변환하면 메모 필드도 비어 있으므로 두 번 변환 할 수 없습니다.

도움이 되었습니까?

해결책

결국 스스로 일을해야했지만 앞으로 다른 사람을 도울 수 있습니다.

        public static object GetDbaseOrFoxproRawValue(string DBPath, string TableName, string ColumnName, 
        string CompareColumnName, string CompareValue, bool CompareColumnIsAutoKey)
    {
        using (BinaryReader read = new BinaryReader(File.Open(
            Path.Combine(DBPath, TableName + ".dbf"), FileMode.Open, FileAccess.Read, FileShare.ReadWrite)))
        {
            // Is it a type of file that I can handle?
            if (new byte[] { 0x02, 0x03, 0x30, 0x43, 0x63, 0x83, 0x8b,
                             0xcb, 0xf5, 0xfb }.Contains(read.ReadByte()))
            {
                // Skip date.
                read.BaseStream.Seek(3, SeekOrigin.Current);

                // Read useful datas...
                uint RecordCount = read.ReadUInt32();
                ushort FirstRecord = read.ReadUInt16();
                ushort RecordLength = read.ReadUInt16();
                int FieldCount = FirstRecord - 296 / 32;

                // Make sure things aren't stupid.
                ColumnName = ColumnName.ToLower();
                CompareColumnName = CompareColumnName.ToLower();

                // Find target column (field)
                string temp;
                UInt32 CompareFieldOffset = uint.MaxValue, FieldOffset = uint.MaxValue;
                byte CompareFieldLength = 0, FieldLength = 0;
                char FieldType = ' ';
                for (int i = 0; i < FieldCount; i++)
                {
                    read.BaseStream.Seek(32 + (i * 32), SeekOrigin.Begin);
                    temp = Encoding.ASCII.GetString(read.ReadBytes(11)).Replace("\0", "").ToLower();
                    if (temp == CompareColumnName)
                    {
                        read.ReadChar();
                        CompareFieldOffset = read.ReadUInt32();
                        CompareFieldLength = read.ReadByte();
                    }
                    if (temp == ColumnName)
                    {
                        FieldType = read.ReadChar();
                        FieldOffset = read.ReadUInt32();
                        FieldLength = read.ReadByte();
                    }

                    if (CompareFieldOffset != uint.MaxValue && FieldOffset != uint.MaxValue)
                        break;
                }

                // Make sure we can continue.
                if (CompareFieldOffset == uint.MaxValue || 
                    FieldOffset == uint.MaxValue) return null;

                // Iterate through each record to find the one we want.
                for (int index = 0; index < RecordCount; index++)
                {
                    read.BaseStream.Seek(FirstRecord + (index * RecordLength) + CompareFieldOffset, SeekOrigin.Begin);
                    temp = Encoding.Default.GetString(read.ReadBytes(CompareFieldLength)).Replace("\0", "");
                    if (temp == CompareValue)
                    {
                        read.BaseStream.Seek(FirstRecord + (index * RecordLength) + FieldOffset, SeekOrigin.Begin);
                        switch (FieldType)
                        {
                            case 'M':
                            case 'I': return read.ReadUInt32();
                            case 'C':
                            default: return Encoding.Default.GetString(read.ReadBytes(FieldLength)).Replace("\0", "");
                        }
                    }
                }
            }
            else
            {
                return null;
            }
        }

        return null;
    }

그 결과를 가져 와서 메모 파일의 색인으로 사용하십시오 (이 코드는 MSDN 문서를 사용하여 매우 간단합니다).

다른 팁

나는 C# 또는 FoxPro 또는 SQL Server에 대해 크게 익숙하지 않으므로 그와 관련하여 많은 조언을 드릴 수 없습니다.

그러나 적절한 드라이버를 찾을 수없는 경우 원시 데이터 및 메모 파일을 직접 구문 분석하는 것을 고려할 수 있습니다. 또 다른 질문은 이것을 다루었습니다.

Python에서 FoxPro DBF 파일을 읽는 가장 쉬운 방법은 무엇입니까?

믿거 나 말거나,이 파일 형식은 자신의 C# parser를 작성하기로 결정하면 구문 분석하기가 매우 간단합니다. 이 사양은 Microsoft에서 사용할 수 있습니다.

ODBC를 사용하여 VFP 8 테이블을 연결하고 메모 필드는 문제없이 작동합니다. OLEDB가 다른지 모르겠습니다.

여기에는 Visual FoxPro 테이블이 없을 수도 있습니다. 많은 VFP 시스템은 FoxPro 2 또는 DBase 응용 프로그램과 동일한 테이블을 대체합니다. 파일 헤더를 보거나 다른 ODBC 드라이버 중 하나를 시도하여 작동하는지 확인할 수 있습니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top