C: read/write
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了C: read/write相关的知识,希望对你有一定的参考价值。
参考技术A read() 函数从打开的设备或文件中读取数据,其函数原型如下:参数count是请求读取的字节数,读上来的数据保存在缓冲区buf中,同时文件的当前读写位置向后移。当函数调用成功返回的是读取的字节数,出错返回-1并设置errno,如果在调read之前已到达文件末尾,则这次read返回0。
有些情况下,实际读到的字节数(返回值)会小于请求读的字节数count,例如:
write函数向打开的设备或文件中写数据:
与 read() 类似,写常规文件时, write的返回值通常等于请求写的字节数count,而向终端设备或网络写则不一定
对于不同的文件, read() 函数的阻塞情况不同:
同样,写常规文件是不会阻塞的,而向终端设备或网络写则不一定
对 Volatile.Read/Write 的理解
【中文标题】对 Volatile.Read/Write 的理解【英文标题】:understanding of Volatile.Read/Write 【发布时间】:2014-08-10 00:29:57 【问题描述】:我正在尝试理解 C# Volatile 类。
如我所见:
Volatile.Write
方法强制写入 location 中的值
到通话点。此外,任何早期的程序顺序
加载和存储必须在调用 Volatile.Write 之前发生。
Volatile.Read
方法强制读取位置中的值
在通话点。此外,任何以后的程序顺序加载
并且存储必须在调用 Volatile.Read 之后发生。
这是否意味着在以下情况下:
internal sealed class ThreadsSharingData
private Int32 m_flag = 0;
private Int32 m_value = 0;
// This method is executed by one thread
public void Thread1()
// Note: 5 must be written to m_value before 1 is written to m_flag
m_value = 5;
Volatile.Write(ref m_flag, 1);
// This method is executed by another thread
public void Thread2()
// Note: m_value must be read after m_flag is read
if (Volatile.Read(ref m_flag) == 1)
Console.WriteLine(m_value);
cpu 会等待Volatile.Write(ref m_flag, 1);
之前的命令,然后再开始写入m_flag
?
这对线程同步有何帮助?
【问题讨论】:
它仅与内存模型较弱的处理器相关,即获取和释放语义很重要的处理器。除了ARM内核之外,剩下的很少。它不是正确同步的替代品,编写没有同步的线程安全代码是一个非常先进的概念。否则,this question 已经很好地涵盖了。 【参考方案1】:cpu 将等待 Volatile.Write(ref m_flag, 1); 之前的命令在开始写入 m_flag 之前?
哎呀,有点。更好的表达方式是:可以保证,如果任何其他线程看到 m_flag
设置为 1,他们也会看到 m_value
设置为 5。
这对线程同步有何帮助?
我不会说它有助于同步 - 但它确实有助于实现正确性。
如果您不使用 volatile 读取/写入,编译器/运行时/cpu 可能会重新排序 Thread1
方法中的两条指令,并且程序将能够打印 0、5 或什么都没有。
使用易失性读/写,程序将打印 5 或根本不打印,但从不 0。这是预期的行为。
【讨论】:
【参考方案2】:这对线程同步有何帮助?
从设置命令执行顺序的意义上说,它无助于线程同步。它使您可以确保并发线程以特定顺序观察内存中值的更改,以防特定顺序对您的程序逻辑很重要。
[是否] CPU 在开始写入
m_flag
之前等待Volatile.Write(ref m_flag, 1);
之前的命令?
不,写入m_value
的命令已经执行。但是,它的结果可能在 CPU 内核之外不可见 - 特别是,运行在不同内核上的线程可能会从 m_value
读取旧值 在向其写入 5
的命令之后执行完毕。这是因为新值可能在 CPU 的缓存中,而不是在内存中。
如果你写
m_value = 5;
m_flag = 1;
而不是Volatile.Write(ref m_flag, 1)
,另一个核心可能会以不同的顺序看到写入:首先它会看到m_flag
变成1
,然后它会看到m_value
变成5
。如果你的其他线程使用m_flag
的值来判断m_value
的有效性,那么逻辑可能会被破坏:例如Thread2
可能偶尔会打印零。
【讨论】:
以上是关于C: read/write的主要内容,如果未能解决你的问题,请参考以下文章
linux下的read函数、write函数是属于直接I/O,为啥函数原型的第二项就是要将数据放到输入缓冲区内呢?
index [XXX] blocked by: [FORBIDDEN/12/index read-only / allow delete (api)]问题解决
关于readsCount、RPKM/FPKM、RPM(CPM)、TPM的理解
jxl读取excel导入到数据库,报错java.lang.NoClassDefFoundError: jxl/read/biff/BiffException