首页 > 其他分享 >学习笔记7

学习笔记7

时间:2023-10-29 14:33:35浏览次数:36  
标签:attr int void 笔记 学习 线程 pthread row

第四章总结

并行计算导论

要求解某个问题,先要设计一种算法,描述如何一步步地解决问题,然后用计算机程序以串行指令流的形式实现该算法。在只有一个 CPU的情况下,每次只能按顺序执行某算法的一个指令和步骤。但是,基于分治原则(如二又树查找和快速排序等)的算法经常表现出高度的并行性,可通过使用并行或并发执行来提高计算速度。并行计算是一种计算方案,它尝试使用多个执行并行算法的处理器更快速地解决问题。

  • 顺序算法与并行算法
    描述顺序算法,常用的方法是用一个begin-end代码块列出算法;并行算法使用cobegin-coend代码块来指定并行算法的独立任务。如下图所示:
  • 并行性与并发性
    • 在理想情况下,并行算法中的所有任务都应该同时实时执行。
    • 真正的并行执行只能在有多个处理组件的系统中实现,比如多处理器或多核系统。
    • 在单CPU系统中,一次只能执行一个任务。在这种情况下,不同的任务只能并发执行,即在逻辑上并行执行。

线程

  • 线程的原理
    • 线程是某进程同一地址空间上的独立执行单元。创建某个进程就是在一个唯一地址空间创建一个主线程。当某进程开始时,就会执行该进程的主线程。
  • 线程的优点
    • 线程创建和切换速度更快
    • 线程的响应速度更快
    • 线程更适合并行运算
  • 线程的缺点
    • 由于地址空间共享,线程需要来自用户的明确同步。
    • 许多库函数可能对线程不安全。通常,任何使用全局变量或依赖于静态内存内容的函数,线程都不安全。
    • 在单CPU系统上,使用线程解决问题实际上要比使用顺序程序慢。

线程操作

  • 线程的执行轨迹与进程类似。线程可在内核模式或用户模式下执行。在用户模式下,线程在进程的相同地址空间中执行,但每个线程都有自己的执行堆栈。

线程管理函数

  • 创建线程

    • 使用pthread_create()
      int pthread_create(pthread_t *pthread_id,pthread_attr_t *attr,void *(*func)(void*),void *arg)
    • attr 参数的使用步骤。
      • 定义一个pthread属性变量pthread attr tattr。
      • 用pthread attrinit (&attr)初始化属性变量。
      • 设置属性变量并在pthread create0)调用中使用。
      • 必要时,通过pthread attr destroy (&attr)释放attr 资源。
  • 线程ID
    int pthread_equal(pthread_t t1,pthread_t t2);
    如果是不同的线程,返回0,否则返回非0

  • 线程终止
    int pthread_exit(void *status);
    进行显式终止,其中状态是线程的退出状态。

  • 线程连接
    int pthread_join(pthread_t thread,void **status_ptr)
    终止线程的退出状态以status_ptr返回。

线程示例程序

  • 实践1:用线程计算矩阵的和
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#define N 4
int A[N][N], sum[N];
void *func(void *arg)
{
    int j, row;
    pthread_t tid = pthread_self();
    row = (int)arg;	
    printf("Thread %d [%lu] computes sum of row %d\n", row, tid, row); 
    for (j=0; j<N; j++)
    {
        sum[row] += A[row][j];
    }
    printf("Thread %d [%lu] done sum[%d] = %d\n",row, tid, row, sum[row]);
    pthread_exit((void*)0);
}

int main (int argc, char *argv[])
{
    pthread_t thread[N];	
    int i, j, r, total = 0;
    void *status;
    printf("Main: initialize A matrix\n");

    for (i=0; i<N; i++)
    {
        sum[i] = 0;
        for (j=0; j<N; j++)
        {
            A[i][j] = i*N + j + 1;
            printf("%4d" ,A[i][j]);
        }
    printf("\n");
    }
    printf("Main: create %d threads\n", N);
    for(i=0; i<N; i++)
    {
        pthread_create(&thread[i], NULL, func, (void *)i);
    }
    printf("Main: try to join with threads\n");
    for(i=0; i<N; i++) 
    {
        pthread_join(thread[i], &status);
        printf("Main: joined with %d [%lu]: status=%d\n",i, thread[i], (int)status);
    }
    printf("Main: compute and print total sum:"); 
    for (i=0; i<N; i++)
    {
        total += sum[i];
    }
    printf("tatal = %d\n", total); 
    pthread_exit(NULL);
}

  • 实践2:用线程快速排序
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#define N 4
int A[N][N], sum[N];
void *func(void *arg)
{
    int j, row;
    pthread_t tid = pthread_self();
    row = (int)arg;	
    printf("Thread %d [%lu] computes sum of row %d\n", row, tid, row); 
    for (j=0; j<N; j++)
    {
        sum[row] += A[row][j];
    }
    printf("Thread %d [%lu] done sum[%d] = %d\n",row, tid, row, sum[row]);
    pthread_exit((void*)0);
}

int main (int argc, char *argv[])
{
    pthread_t thread[N];	
    int i, j, r, total = 0;
    void *status;
    printf("Main: initialize A matrix\n");

    for (i=0; i<N; i++)
    {
        sum[i] = 0;
        for (j=0; j<N; j++)
        {
            A[i][j] = i*N + j + 1;
            printf("%4d" ,A[i][j]);
        }
    printf("\n");
    }
    printf("Main: create %d threads\n", N);
    for(i=0; i<N; i++)
    {
        pthread_create(&thread[i], NULL, func, (void *)i);
    }
    printf("Main: try to join with threads\n");
    for(i=0; i<N; i++) 
    {
        pthread_join(thread[i], &status);
        printf("Main: joined with %d [%lu]: status=%d\n",i, thread[i], (int)status);
    }
    printf("Main: compute and print total sum:"); 
    for (i=0; i<N; i++)
    {
        total += sum[i];
    }
    printf("tatal = %d\n", total); 
    pthread_exit(NULL);
}

线程同步

多个线程试图修改同一共享变量或数据结构时,如果修改结果取决于线程的执行顺序,则称之为竞态条件。在并发程序中,绝不能有竞态条件。否则,结果可能不一致。

  • 互斥量
    • 最简单的同步工具是锁,它允许执行实体仅在有锁的情况下才能继续执行。在 Pthread中,锁被称为互斥量,意思是相互排斥。
    • 静态方法
    • 动态方法
  • 死锁预防
    • 互斥量使用封锁协议。
    • 在任何封锁协议中,误用加锁可能会产生一些问题。
    • 死锁是一个状态,在这种状态下,许多执行实体相互等待,无法继续进行下去
  • 条件变量
    • 静态方法
    • 动态方法
  • 生产者-消费者问题
    共享全局变量:
int buf[NBUF];
int head,tail;
int data;
  • 信号量
    • 信号量是进程同步的一般机制。
    • 在使用信号量之前,必须使用一个初始值和一个空等待队列进行初始化。
  • 屏障
    • 在 Pthreads中,可以采用的机制是屏障以及一系列屏障函数。
  • 用并发线程解线性方程组
  • Linux中的线程
    • Linux不区分进程和线程。
    • 对于Linux内核,线程只是一个与其他进程共享某些资源的进程。
    • 在 Linux 中,进程和线程都是由 clone()系统调用创建的:
      int clone(int (*fn)(void*),void *child_stack,int flags,void *arg)

苏格拉底挑战

  • 关于线程的苏格拉底挑战

  • 关于线程同步的苏格拉底挑战

遇到的问题

什么时候适合死锁?

标签:attr,int,void,笔记,学习,线程,pthread,row
From: https://www.cnblogs.com/gao0818/p/17795862.html

相关文章

  • 2023-2024-1学期 20231424 《计算机基础与程序设计》第5周学习总结
    2023-2024-1学期20231424《计算机基础与程序设计》第5周学习总结作业信息作业属于的课程<班级链接>(2022-2023-1-计算机基础与程序设计)作业要求<作业要求链接>(2022-2023-1计算机基础与程序设计第一周作业)这个作业的目标《计算机科学概论》第6章和《C语言程序......
  • Unity学习笔记--入门
    Unity引擎学习入门:Unity中的坐标系:左手坐标系(z轴正方向向里面)x轴:平行屏幕向右正方向y轴:平行屏幕向上正方向Z轴:垂直屏幕向内为正方向【补】openGL是右手坐标系DirectX是左手坐标系窗口:窗口布局Layout:Scene这里我们可以看见所有的场景内容。窗口上的工具栏:有关......
  • 《信息安全系统设计与实现》第八周学习笔记
    《信息安全系统设计与实现》第八周学习笔记第四章并发编程并行计算尝试使用多个执行并行算法的处理器更快速的解决问题顺序算法与并行算法顺序算法:所有步骤通过单个任务依次执行,每次执行一个步骤,当所有步骤执行完成时,算法结束。并行算法:cobegin-coend代码块来指定独立......
  • Oracle RAC 的简单学习
    OracleRAC的概念OracleRAC(RealApplicationClusters)是Oracle数据库管理系统的一个功能,它允许将数据库实例部署在多个节点上,实现高可用性和可伸缩性。通过将数据库实例分散在不同的服务器上,OracleRAC提供了系统级别的容错能力,即使在一个节点故障的情况下,数据库仍然可......
  • win10 openocd通过vscode远程调试stm32的uboot--Apple的学习笔记
    一,前言我在uboot支持的cortex-M4内核启动流程分析--Apple的学习笔记中就说过了,我计划要单步调试uboot,但是我只有stlink,所以要基于openocd的gdb来调试,所以就做了尝试,花费约2天时间,虽然做了些无用功,专门还装了ubuntu18.04,且基于ubuntu还安装了openocd这些其实都无用的,但是就是这些过......
  • pytorch深度学习入门
    参考:1、Pytorch最全入门介绍,Pytorch入门看这一篇就够了2、torch.nn模块torch.nn模块是PyTorch中用于构建神经网络的核心模块,包含了各种不同类型的层(如全连接层、卷积层、池化层)、损失函数、优化器等。下面介绍torch.nn中常用的一些类和函数:nn.module:所有神经网络层的基类,定义了......
  • 力扣学习笔记——49. 字母异位词分组
    49.字母异位词分组https://leetcode.cn/problems/group-anagrams/?envType=study-plan-v2&envId=top-100-liked给你一个字符串数组,请你将字母异位词组合在一起。可以按任意顺序返回结果列表。字母异位词是由重新排列源单词的所有字母得到的一个新单词。示例1:输入:strs=[......
  • [量化投资-学习笔记002]Python+TDengine从零开始搭建量化分析平台-MA均线的多种实现方
    MA均线时最基本的技术指标,也是最简单,最不常用的(通常使用EMA、SMA)。以下用两种不同的计算方法和两种不同的画图方法进行展示和说明。MA均线指标公式MA(N)=(C1+C2+C3+…+CN)/N目录方式一1.SQL直接查询均值2.使用pyplot进行绘图3.使用Grafana绘图方式二1.使用Python计......
  • 第四章学习笔记
    1.计算导论计算导论是学习用户级线程的基础。在Unix/Linux系统中,线程是进程的一部分,它们共享相同的地址空间和系统资源。用户级线程是在用户空间管理的线程,而内核级线程是由操作系统内核管理的线程。2.线程线程是程序执行的基本单位,它包括线程的创建、启动、暂停、终止等操作......
  • 玉米病害检测:基于深度学习的YOLO模型的应用【玉米病害检测实战】
    随着人工智能技术的快速发展,其在农业领域的应用也越来越广泛。玉米作为重要的粮食作物之一,在生长过程中容易受到各种病害的侵害,这对玉米产量和质量造成了严重的影响。因此,利用人工智能技术对玉米病害进行快速准确的检测和诊断具有重要的意义。本文将介绍基于深度学习的YOLO(YouOnly......