2017-07-14 7 views
2

概要:.netランダムアクセスファイルでレコードをロックすると、ファイル内のロックされたレコードより先にレコードにアクセスすることはできません。.netファイルランダムアクセスrecoardロック

問題を示すために、2つの簡単なプログラムを作成して、レコードを開き、レコードをロックし、もう1つは読み込みを試みます。

結果は、最初のプログラムでレコード番号9をロックすると、レコード1とレコード2を読み取ることができますが、それ以上は読み取れません。期待(これはVB6での私たちの経験です)は、ロックしたレコードとは別にすべてのレコードを読み取ることができるということです。

誰でもこの問題を見ていますか?私は何か変なことをしていますか?どんな仕事?

デモコード:

プログラム1 /オープン/ロック

Sub Main() 

    Dim FileName As String = "test.a" 
    Dim ListofName() As String = {"Name1", "Name2", "Name3", "Name4", 
      "Name5", "Name6", "Name7", "Name8", "Name9", "Name10"} 

    Try 

     Dim FileNumber1 As Integer = FreeFile() 
     FileOpen(FileNumber1, FileName, OpenMode.Random, 
       OpenAccess.ReadWrite, OpenShare.Shared, 600) 

     FileGet(FileNumber1, People, 1) 

     'Create File if needs be 
     If People.Name = "" Then 
      For A = 1 To 10 
       People.Name = ListofName(A - 1) 
       FilePut(FileNumber1, People, A) 
      Next 
     End If 

     'Lock the recoard we want for testing 
     Lock(FileNumber1, 9) 

    Catch ex As Exception 
     FileClose() 
    End Try 
    FileClose() 
End Sub 

_

プログラム2オープンを作成し、試してみて、読み

Sub Main() 

    Dim FileName As String = "C:\**Location of first program file**\test.a" 

    Try 

     Dim FileNumber1 As Integer = FreeFile() 
     FileOpen(FileNumber1, FileName, OpenMode.Random, 
       OpenAccess.ReadWrite, OpenShare.Shared, 600) 

     FileGet(FileNumber1, People, 2) 

     'See how much of the file we can read 
     For A = 1 To 10 
      FileGet(FileNumber1, People, A) 
      System.Diagnostics.Debug.WriteLine(People.Name.ToString) 
     Next 

    Catch ex As Exception 
     FileClose() 
    End Try 
    FileClose() 
End Sub 

編集0.1:個々のレコードがファイル内でロックされているほど、ロックされたレコードよりも多くのバイト/レコードにアクセスできなくなることがわかりました。

+0

urg ... start using System.IO。とにかく、ファイルがすぐに「完全に」書かれているとは限らず、ストリームを閉じるかフラッシュする必要があります。 –

+0

なぜvb6タグですか? vb6!= vb.net。 –

+0

互換性ライブラリのバグかもしれません。文書化された動作は 'Lock'が単一のレコードだけをロックすることです。 – Craig

答えて

0

ご意見ありがとうございます。

MSDN hereで同じ質問を投稿し、その回答を得ることができました。

だから、結論はあなたがFILEGETか(例えばSystem.IO.BinaryReader.ReadDoubleを())を使用する場合、.NETで、読者はあなたが望むものを読み込むだけでなく、先行内でそのロックされたレコードを意味するコンテンツをバッファリングするだけでなくということですファイルがヒットして読み込みに失敗します。 System.IO.FileStream.Readを(使用)と正確なバイト数を指定する場合

は、しかし、あなたは、あなたがロックされた1

以外のファイルのすべてのレコードを読み取ることができるようにバッファが作成されていませんしたいですコード例:

<StructLayout(LayoutKind.Sequential, CharSet:=CharSet.Ansi, Pack:=1)> 
Structure Person 
    <MarshalAs(UnmanagedType.ByValTStr, SizeConst:=600)> 
    <VBFixedString(600)> 
    Dim name As String 
End Structure 

. . . 

Using fs = New FileStream(FileName, FileMode.Open, FileAccess.ReadWrite, FileShare.ReadWrite, Marshal.SizeOf(People)) 
For A = 1 To 10 
    Try 
    Console.WriteLine("Trying " & A & "...") 

    Dim b() As Byte 
    ReDim b(Marshal.SizeOf(People) - 1) 
    fs.Seek((A - 1) * Marshal.SizeOf(People), SeekOrigin.Begin) 
    fs.Read(b, 0, b.Length) 
    Dim h = GCHandle.Alloc(b, GCHandleType.Pinned) 
    People = Marshal.PtrToStructure(Of Person)(h.AddrOfPinnedObject()) 
    h.Free() 
    Console.WriteLine(People.name.Trim()) 

    Catch ex As Exception 
    Console.WriteLine("ERROR " & A & " " & ex.Message) 
    End Try 
Next 
End Using 
関連する問題