访问 C 数组中的不同元素线程安全吗?

问题描述 投票:0回答:4

假设我有以下 C 代码:

int my_global_arr[100];

或者更一般地说,

some_type *my_global_arr = malloc(some_size * sizeof(some_type);

在多个线程中同时访问(读和写)不同元素是否安全?
例如,如果我有

void *my_thread(void *index){
    int idx = *((int *)(index));
    my_global_arr[idx] = idx;
    return NULL;
}

并且在

main()

int a = 1;
int b = 2;
pthread_t thread1, thread2;
pthread_create(&thread1, NULL, my_thread, &a);
pthread_create(&thread2, NULL, my_thread, &b);

pthread_join(thread1, NULL);
pthread_join(thread2, NULL);

能保证两个线程不会互相干扰吗?

我的实验:
我尝试在 x86_64 CPU 上运行上面的“程序”,扩展到 1000 个线程,100000 次 使用GCC 8.3.0,-std=c99,看起来它们不会互相干扰; 然而,我认为这样的实验不足以得出这样的访问是 在所有平台上线程安全。

编辑1
这个问题是关于访问不同的 different 元素 线程,不同线程中不能有相同的元素;那是, 例如,

thread-1
读取/写入
arr[1]
thread-2
读取/写入
arr[2]

c multithreading thread-safety pthreads
4个回答
3
投票

如果你能保证在同一时刻每个元素只能被一个线程访问,那么它就是线程安全的。因为数组的每个元素都彼此不同(物理上),这意味着它们是内存的独立部分。


3
投票

[已编辑]

在 C 中访问数组的不同元素是完全线程安全的。


1
投票

访问不同元素始终是 100% 安全的。


0
投票

这个问题问得好。如果CPU的基本操作在32位内存上进行,那么在线程1中CPU将读取32位,更新左边的16位,然后写回32位。这将覆盖右侧的 16,该值可能已被线程 2 在线程 1 读取和写入之间更改。然而,我们希望原始问题的作者不是第一个想到这一点的人,并且在现实世界中,编译器编写者会采取步骤来发出正确的代码。最简单的方法是在 32 位边界上对齐数组元素,即使大小为 16。

© www.soinside.com 2019 - 2024. All rights reserved.