.net文件随机访问重新锁定

时间:2017-07-14 15:06:40

标签: vb.net vb6 locking

摘要 .net 在随机访问文件中锁定记录时,我们无法访问文件中锁定记录之前的记录。

为了演示这个问题,我写了两个简单的程序,一个打开并锁定一个记录,另一个试图通读。

结果是,当在第一个程序中锁定10个记录中的第9个记录时,我们能够读取记录1和2,但不能再记录!期望(这是我们对VB6的体验)是你应该能够读取你锁定的所有记录。

有没有人见过这个问题?我做了一件奇怪的事吗?有什么工作吗?

演示代码:

计划1创建/打开/锁定

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

_

计划2打开并尝试阅读

<script type="text/javascript">

$('a[href="#sectionB"]').on('shown', function (e) {
    initMap();
});


function initMap() {
    var uluru = {lat: -34.031342, lng: 18.577419};
    var map = new google.maps.Map(document.getElementById('map'), {
        zoom: 16,
        center: uluru,
        mapTypeId: 'satellite'

    });

    var marker = new google.maps.Marker({
      position: {lat: -34.031342, lng: 18.577419},
      map: map
    });
    }
</script>
    <script async defer
    src="https://maps.googleapis.com/maps/api/js?key=MYKEYHERE&callback=initMap">
    </script>

编辑0.1:我们发现单个记录在文件中被锁定得越深,锁定的字节/记录就越难以访问。

1 个答案:

答案 0 :(得分:0)

感谢大家的评论。

在MSDN here上发布了相同的问题,并设法得到答案。

  

所以结论是使用.net如果你使用FileGet或(例如System.IO.BinaryReader.ReadDouble())读者不仅会读取你想要的内容而且还会缓冲内容,这意味着文件中前面的锁定记录是点击导致读取失败。

     

但是当使用System.IO.FileStream.Read()并且确切地指定了你想要的字节数时,不会创建缓冲区,允许你读取除锁定文件之外的文件中的所有记录

代码示例:

<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