实战算法优化

本文介绍了算法优化中使用的Intrinsic函数,这些函数允许程序员使用向量化操作,提高计算效率。内容包括计算类型的Intrinsic函数、设置初始化向量数组的方法、从内存加载数据的技巧以及在图像处理中的应用。同时,文章还探讨了编译器内置函数,如用于指令缓存刷新和数据预取的函数,以优化性能。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

引言

对于这方面的姿势,也是属于意外。在使用Caffe的过程中,需要依赖一个关于矩阵计算的库,可是
使用atlas或者openblas, 当然有资金支持的话可以使用更快地MKL, 而一个穷小白就只能从开源免费的计算库中选了,就选了OpenBlas。 后来因为缘分,认识了OpenBlas的创始人,从他们公司的工作中了解到还有机器学习算法优化加速的这么个工作。其中涉及到如OpenMP, SIMD, 当然编译器优化也是不容忽视的。在此,总结一下工作中用到的一些函数,免得下次见到不认识了。

Intrinsic function[^1]

在这里插入图片描述
我对这个的理解就是在汇编的基础上进行向量化的封装的一些宏或者函数, 同时可以操作很多个数据,如使用SSE可以操作128位的数据,可以使4个int类型,也可以使用8个short类型也可以是16个char类型的数据。

从intrinsic guide[^2]中就可以看出Intel关于SIMD方面的发展历程。MMX(主要是16位指令)到后面的SSE2 SSE4.2(32位指令)等等。 查阅文档的时候后可以按照计算的类别:

计算类型

计算类型根据操作数据的类型分别封装了加减乘除,文档中对接口函数说明得很是清楚,还包括生成目标指令是什么。如:

 Synopsis
    __m128i _mm_add_epi16 (__m128i a, __m128i b)
    #include "emmintrin.h"
    Instruction: paddw xmm, xmm
    CPUID Flags: SSE2
Description
    Add packed 16-bit integers in a and b, and store the results in dst.
Operation
    FOR j := 0 to 7
        i := j*16
        dst[i+15:i] := a[i+15:i] + b[i+15:i]
    ENDFOR

从外,函数命名很有规律 _mm_操作_操作的数据类型, 数据类型__m128i 表示integer类型的向量数组,__m128表示单精度类型的向量数组,__128d表示双精度类型的向量数组。

__m128i _mm_add_epi16 (__m128i a, __m128i b); //Add packed 16-bit integers in a and b
__m128d _mm_div_pd (__m128d a, __m128d b); // Divide packed double-precision (64-bit) floating-point elements in a by packed elements in b
__m128d _mm_mul_sd (__m128d a, __m128d b); // Multiply the lower double-precision (64-bit) floating-point element in a and b, store the result in the lower element of dst, and copy the upper element from a to the upper element of dst.
__m128i _mm_subs_epi16 (__m128i a, __m128i b)
__m128i _mm_subs_epu16 (__m128i a, __m128i b)

设置\初始化向量数组

__m128i _mm_set_epi16 (short e7, short e6, short e5, short e4, short e3, short e2, short e1, short e0);
__m128i _mm_set_epi32 (int e3, int e2, int e1, int e0);

__m128i _mm_set_epi8 (char e15, char e14, char e13, char e12, char e11, char e10, char e9, char e8, char e7, char e6, char e5, char e4, char e3, char e2, char e1, char e0);

__m128d _mm_set_pd (double e1, double e0);

__m128d _mm_set_pd1 (double a); // Broadcast double-precision (64-bit) floating-point value a to all elements of dst.

__m128 _mm_set_ps (float e3, float e2, float e1, float e0);
__m128 _mm_set_ps1 (float a);
__m128d _mm_set_sd (double a);
__m128 _mm_set_ss (float a);
__m128i _mm_set1_epi16 (short a);

__m128i _mm_set1_epi32 (int a);

__m128i _mm_set1_epi64 (__m64 a);

__m128i _mm_set1_epi64x (__int64 a);
__m128i _mm_set1_epi8 (char a);
__m128d _mm_set1_pd (double a);
__m128 _mm_set1_ps (float a);
__m128i _mm_setr_epi16 (short e7, short e6, short e5, short e4, short e3, short e2
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值