MMX及SSE优化--SSE篇

C/C++指令集介绍以及优化(主要针对SSE优化) 前言:最近在做一些OpenCV的优化相关的东西,发现OpenCV现在的执行效率很高的原因一部分是来自于底层的优化,比如指令集优化,但是一直没找到比较系统性的关于CPU指令集优化的文章或者是书籍,于是自己打算做一个总结,鉴于水平有限,有不正确的地方还望有大佬指正。 一、CPU指令集优化的概述 1.1 数据并行的两种实现 在计算机体系中,数据并行有两种实现路径: MIMD(Multipl... 阅读详情

 上回讲到针对整数运算的MMX优化技术,然而真正大运算量的图形和声音处理大都用的是浮点运算,而且现在对浮点运算的要求也是越来越高,在这样一个条件下INTEL终于在Pentium III处理中增加针对浮点运算优化的SSE指令,所以所有用过SSE指令的程序必须在Pentium III或者Althon XP以后的CPU上才来运行。

 SSE全新定义了8个新的128位寄存器xmm0-xmm7,比MMX的64位还提高了1倍,每个寄存器可以同时装入4个32位的浮点数,因为是全新的寄存器,所以少了MMX寄存器与原浮点寄存器的切换工作,所以有了更高的执行效率。值得注意的SSE还可以对16位和8位的整数进行运算,不过这已经不是SSE应用的主流了。

 在这里随便提一个Intel Compiler 8.0,这个编译器的优化能力的确是强,个人感觉大概比Visual C++ 6.0 SP6快10-20%左右,它可以针对不同的CPU作出优化,如果你是P4系列的cpu,在编译的时候加上参数/fast /QxW /Qip /Qunroll40,会有意想不到的结果,如果你再阅读一个它的用户手册,按照里面的方法稍微修改一下程序将会有更多提高,向所有崇拜极限优化的朋友推荐这款编译器。题外话少说,再次转入SSE正题,下面还是给出一个简单的例子:

在VC中使用内联汇编
float a[]={1.0,2.0,3.0,4.0};
float b[]={5.0,6.0,7.0,8.0};
_asm{
mov ecx,a;
mov edx,b;
movaps xmm0,[ecx];
movaps xmm1,[edx];
addps xmm0,xmm1;
movaps [ecx],xmm0;
}

跟MMX一样也可以不用汇编只用包含一个头文件就可以直接在C里面使用了:
#include
__m128 a = _mm_set_ps(1, 2, 3, 4)
__m128 b = _mm_set_ps(5, 6, 7, 8)
a = _mm_add_ps(a, b);
这个时候就感觉使用Intrinsics方便多了,因为它制定了好多合成的伪指令,方便了不少。

下面顺便贴一段SSE的部分指令介绍,更全的可以找Intel下载指令手册。下面这部分是引用至:
http://dwbclz.myetang.com/articles/piii/sse-ins-ref.html


ADDPS

格式:ADDPS xmm1, xmm2/m128

功能:两组单精度数相加

算法:

DEST[31-0] = DEST[31-0] + SRC/m128[31-0] ;
DEST[63-32] = DEST[63-32] + SRC/m128[63-32] ;
DEST[95-64] = DEST[95-64] + SRC/m128[95-64] ;
DEST[127-96] = DEST[127-96] + SRC/m128[127-96];

ADDSS

格式:ADDSS xmm1, xmm2/m32

功能:低位单精度数相加

算法:

DEST[31-0] = DEST[31-0] + SRC/m32[31-0];
DEST[63-32] = DEST[63-32] ;
DEST[95-64] = DEST[95-64] ;
DEST[127-96] = DEST[127-96];
 
ANDNPS

格式:ANDNPS xmm1, xmm2/m128

功能:xmm1“取反”再和 xmm2/m128 求“与”运算

算法:

DEST[127-0] = NOT (DEST[127-0]) AND SRC/m128[127-0];

ANDPS

格式:ANDPS xmm1, xmm2/m128

功能:进行两个寄存器的逻辑“与”操作

算法:

DEST[127-0] AND= SRC/m128[127-0];

CMPPS

格式:CMPPS xmm1, xmm2/m128, imm8

功能:比较两个寄存器的数值,根据imm8的不同数值采用不同的比较方法

imm8 == 0, ==; imm8 == 1, <; imm8 == 2, <=; imm8 == 3, ;
imm8 == 4, !=; imm8 == 5, !<; imm8 == 6, !<=; imm8 == 7, !;

算法:

IF (imm8 = 0) THEN
 OP = "EQ";
ELSEIF (imm8 = 1) THEN
 OP = "LT";
ELSEIF (imm8 = 2) THEN
 OP = "LE";
ELSEIF (imm8 = 3) THEN
 OP = "UNORD";
ELSEIF (imm8 = 4) THEN
 OP = "NE";
ELSEIF (imm8 = 5) THEN
 OP = "NLT";
ELSEIF (imm8 = 6) THEN
 OP = "NLE";
ELSEIF (imm8 = 7) THEN
 OP = "ORD";
FI

CMP0 = DEST[31-0] OP SRC/m128[31-0];
CMP1 = DEST[63-32] OP SRC/m128[63-32];
CMP2 = DEST [95-64] OP SRC/m128[95-64];
CMP3 = DEST[127-96] OP SRC/m128[127-96];

IF (CMP0 = TRUE) THEN
 DEST[31-0] = 0XFFFFFFFF;
ELSE
 DEST[31-0] = 0X00000000;
FI
IF (CMP1 = TRUE) THEN
 DEST[63-32] = 0XFFFFFFFF;
ELSE
 DEST[63-32] = 0X00000000;
FI
IF (CMP2 = TRUE) THEN
 DEST[95-64] = 0XFFFFFFFF;
ELSE
 DEST[95-64] = 0X00000000;
FI
IF (CMP3 = TRUE) THEN
 DEST[127-96] = 0XFFFFFFFF;
ELSE
 DEST[127-96] = 0X00000000;
FI

其它:你可以使用下面的可读性良好的指令

指令 实现
CMPEQPS xmm1, xmm2; CMPPS xmm1,xmm2, 0
CMPLTPS xmm1, xmm2; CMPPS xmm1,xmm2, 1
CMPLEPS xmm1, xmm2; CMPPS xmm1,xmm2, 2
CMPUNORDPS xmm1, xmm2; CMPPS xmm1,xmm2, 3
CMPNEQPS xmm1, xmm2; CMPPS xmm1,xmm2, 4
CMPNLTPS xmm1, xmm2; CMPPS xmm1,xmm2, 5
CMPNLEPS xmm1, xmm2; CMPPS xmm1,xmm2, 6
CMPORDPS xmm1, xmm2; CMPPS xmm1,xmm2, 7

CMPSS

格式:CMPSS xmm1, xmm2/m32, imm8

功能:低位单精度数做比较

算法:算法同CMPPS相似,只不过只是针对DEST[31-0]进行操作。

同样也可以利用可读性更好的指令

指令 实现
CMPEQSS xmm1, xmm2 CMPSS xmm1,xmm2, 0
CMPLTSS xmm1, xmm2 CMPSS xmm1,xmm2, 1
CMPLESS xmm1, xmm2 CMPSS xmm1,xmm2, 2
CMPUNORDSS xmm1, xmm2 CMPSS xmm1,xmm2, 3
CMPNEQSS xmm1, xmm2 CMPSS xmm1,xmm2, 4
CMPNLTSS xmm1, xmm2 CMPSS xmm1,xmm2, 5
CMPNLESS xmm1, xmm2 CMPSS xmm1,xmm2, 6
CMPORDSS xmm1, xmm2 CMPSS xmm1,xmm2, 7

COMISS

格式:COMISS xmm1, xmm2/m32

功能:比较低位数并且设置标识位

算法:

OF = 0;
SF = 0;
AF = 0;
IF ((DEST[31-0] UNORD SRC/m32[31-0]) = TRUE) THEN
 ZF = 1;
 PF = 1;
 CF = 1;
ELSEIF ((DEST[31-0] GTRTHAN SRC/m32[31-0]) = TRUE)THEN
 ZF = 0;
 PF = 0;
 CF = 0;
ELSEIF ((DEST[31-0] LESSTHAN SRC/m32[31-0]) = TRUE THEN
 ZF = 0;
 PF = 0;
 CF = 1;
ELSE
 ZF = 1;
 PF = 0;
 CF = 0;
FI

CVTPI2PS

格式:CVTPI2PS xmm, mm/m64

功能:32位整数转变为浮点数

算法:

DEST[31-0] = (float) (SRC/m64[31-0]) ;
DEST[63-32] = (float) (SRC/m64[63-32]);
DEST[95-64] = DEST[95-64] ;
DEST[127-96] = DEST[127-96];
CVTPS2PI

格式:CVTPS2PI mm, xmm/m64

功能:低位的两个浮点数转变为整数

算法:

DEST[31-0] = (int) (SRC/m64[31-0]);
DEST[63-32]= (int) (SRC/m64[63-32]);

CVTSI2SS

格式:CVTSI2SS xmm, r/m32

功能:32位整数转变为浮点数,存入低位

算法:

DEST[31-0] = (float) (R/m32);
DEST[63-32] = DEST[63-32] ;
DEST[95-64] = DEST[95-64] ;
DEST[127-96] = DEST[127-96];

CVTSS2SI

格式:CVTSS2SI r32, xmm/m32

功能:低位的浮点数转变为32位整数

算法:

r32 = (int) (SRC/m32[31-0]);

CVTTPS2PI

格式:CVTTPS2PI mm, xmm/m64

功能:低位的两个浮点数转变为整数,并且舍位

算法:

DEST[31-0] = (int) (SRC/m64[31-0]) ;
DEST[63-32] = (int) (SRC/m64[63-32]);

CVTTSS2SI

格式:CVTTSS2SI r32, xmm/ m32

功能:将最低位浮点数转换为整数,并舍位。

算法:

r32 = (INT) (SRC/m32[31-0]);

DIVPS

格式:DIVPS xmm1, xmm2/m128

功能:单精度数除法运算

算法:

DEST[31-0] = DEST[31-0] / (SRC/m128[31-0]) ;
DEST[63-32] = DEST[63-32] / (SRC/m128[63-32]) ;
DEST[95-64] = DEST[95-64] / (SRC/m128[95-64]) ;
DEST[127-96] = DEST[127-96] / (SRC/m128[127-96]);

DIVSS

格式:DIVSS xmm1, xmm2/m32

功能:低位单精度数除法

算法:

DEST[31-0] = DEST[31-0] / (SRC/m32[31-0]);
DEST[63-32] = DEST[63-32] ;
DEST[95-64] = DEST[95-64] ;
DEST[127-96] = DEST[127-96];

EMMS

格式:EMMS

功能:将浮点标识字置空

算法:

FPUTagWord <- FFFF

FXRSTOR

格式:FXRSTOR m512byte

功能:从m512byte中装入FP,MMX,以及SSE的状态

算法:

FP and MMX state and Streaming SIMD Extension state = m512byte;

FXSAVE

格式:FXSAVE m512byte

功能:向m512byte中存入FP,MMX,以及SSE的状态

算法:

m512byte = FP and MMX state and Streaming SIMD Extension state;

LDMXCSR

格式:LDMXCSR m32

功能:装入SSE的状态控制字

算法:

MXCSR = m32;

MAXPS

格式:MAXPS xmm1, xmm2/m128

功能:返回最大值

算法:

IF (DEST[31-0]=NaN) THEN
 DEST[31-0] = SRC[31-0];
ELSEIF (SRC[31-0] = NaN) THEN
 DEST[31-0] = SRC[31-0];
ELSEIF (DEST[31-0] > SRC/m128[31-0]) THEN
 DEST[31-0] = DEST[31-0];
ELSE
 DEST[31-0] = SRC/m128[31-0];
FI
IF (DEST[63-32]=NaN) THEN
 DEST[63-32] = SRC[63-32];
ELSEIF (SRC[63-32] = NaN) THEN
 DEST[63-32] = SRC[63-32];
ELSEIF (DEST[63-32] > SRC/m128[63-32]) THEN
 DEST[63-32] = DEST[63-32];
ELSE
 DEST[63-32] = SRC/m128[63-32];
FI
IF (DEST[95-64]=NaN) THEN
 DEST[95-64] = SRC[95-64];
ELSEIF (SRC[95-64] = NaN) THEN
 DEST[95-64] = SRC[95-64];
ELSEIF (DEST[95-64] > SRC/m128[95-64]) THEN
 DEST[95-64] = DEST[95-64];
ELSE
 DEST[95-64] = SRC/m128[95-64];
FI
IF (DEST[127-96]=NaN) THEN
 DEST[127-96] = SRC[127-96];
ELSEIF (SRC[127-96] = NaN) THEN
 DEST[127-96] = SRC[127-96];
ELSEIF (DEST[127-96] > SRC/m128[127-96]) THEN
 DEST[127-96] = DEST[127-96];
ELSE
 DEST[127-96] = SRC/m128[127-96];
FI

MAXSS

格式:MAXSS xmm1, xmm2/m32

功能:返回低位最大值

算法:同上面类似,区别在于只对DEST[31-0]进行操作

MINPS

格式:MINPS xmm1, xmm2/m128

功能:返回最小值

算法:略

MINSS

格式:MINSS xmm1, xmm2/m32

功能:返回低位最小值

算法:略

MOVAPS

格式:MOVAPS xmm1, xmm2/m128 或 MOVAPS xmm2/m128, xmm1

功能:对齐的数据传输指令

算法:

IF (destination = DEST) THEN
 IF (SRC = m128)THEN (* load instruction *)
 DEST[127-0] = m128;
 ELSE(* move instruction *)
 DEST[127=0] = SRC[127-0];
 FI;
ELSE
 IF (destination = m128)THEN (* store instruction *)
 m128 = SRC[127-0];
 ELSE(* move instruction *)
 DEST[127-0] = SRC[127-0];
 FI;
FI;
 
MOVHLPS

格式:MOVHLPS xmm1, xmm2

功能:高位的两个数传向低位

算法:

DEST[127-64] = DEST[127-64];
DEST[63-0] = SRC[127-64] ;

MOVHPS

格式:MOVHPS xmm, m64 或 MOVHPS m64, xmm

功能:高位数据传输指令

算法:

IF (destination = DEST) THEN(* load instruction *)
 DEST[127-64] = m64;
 DEST[31-0] = DEST[31-0];
 DEST[63-32] = DEST[63-32];
 ELSE (* store instruction *)
 m64 = SRC[127-64];
FI;
 
MOVLPS

格式:MOVLPS xmm, m64 或 MOVLPS m64, xmm

功能:低位数据传输指令

算法:

IF (destination = DEST) THEN(* load instruction *)
 DEST[63-0] = m64;
 DEST[95-64] = DEST[95-64];
 DEST[127-96] = DEST[127-96];
ELSE(* store instruction *)
 m64 = DEST[63-0];
FI
 
MOVLHPS

格式:MOVLHPS xmm1, xmm2

功能:低位的两个数传向高位

算法:

DEST[127-64] = SRC[63-0];
DEST[63-0] = DEST[63-0];

MOVMSKPS

格式:MOVMSKPS r32, xmm

功能:掩码移入32位寄存器

算法:

r32[0] = SRC[31] ;
r32[1] = SRC[63] ;
r32[2] = SRC[95] ;
r32[3] = SRC[127];
r32[7-4] = 0X0 ;
r32[15-8] = 0X00 ;
r32[31-16] = 0X0000 ;

MOVNTPS

格式:MOVNTPS m128, xmm

功能:将数据直接存入内存,减小对缓存的压力

算法:

m128 = SRC;

MOVSS

格式:MOVSS xmm1, xmm2/m32 或 MOVSS xmm2/m32, xmm1

功能:最低位数据的传输指令

算法:

IF (destination = DEST) THEN
 IF (SRC == m32) THEN(* load instruction *)
 DEST[31-0] = m32;
 DEST [63-32] = 0X00000000;
 DEST [95-64] = 0X00000000;
 DEST [127-96] = 0X00000000;
 ELSE(* move instruction *)
 DEST [31-0] = SRC[31-0];
 DEST [63-32] = DEST [63-32];
 DEST [95-64] = DEST [95-64];
 DEST [127-96] = DEST [127-96];
 FI
ELSE
 IF (destination = m32) THEN(* store instruction *)
 m32 = SRC[31-0];
 ELSE (* move instruction *)
 DEST [31-0] = SRC[31-0]
 DEST [63-32] = DEST[63-32];
 DEST [95-64] = DEST [95-64];
 DEST [127-96] = DEST [127-96];
 FI
FI

MOVUPS

格式:MOVUPS xmm1, xmm2/m128 或 MOVUPS xmm2/m128, xmm1

功能:非对齐数据的传输指令

算法:

IF (destination = xmm) THEN
 IF (SRC = m128)THEN(* load instruction *)
 DEST[127-0] = m128;
 ELSE (* move instruction *)
 DEST[127-0] = SRC[127-0];
 FI
ELSE
 IF (destination = m128) THEN(* store instruction *)
 m128 = SRC[127-0];
 ELSE (* move instruction *)
 DEST[127-0] = SRC[127-0];
 FI
FI

MULPS

格式:MULPS xmm1, xmm2/m128

功能:单精度数相乘

算法:

DEST[31-0] = DEST[31-0] * SRC/m128[31-0] ;
DEST[63-32] = DEST[63-32] * SRC/m128[63-32] ;
DEST[95-64] = DEST[95-64] * SRC/m128[95-64] ;
DEST[127-96] = DEST[127-96] * SRC/m128[127-96];

MULSS

格式:MULSS xmm1, xmm2/m32

功能:最低位的单精度数相乘

算法:

DEST[31-0] = DEST[31-0] * SRC/m32[31-0];
DEST[63-32] = DEST[63-32] ;
DEST[95-64] = DEST[95-64] ;
DEST[127-96] = DEST[127-96];

ORPS

格式:ORPS xmm1, xmm2/m128

功能:求或运算

算法:

DEST[127-0] |= SRC/m128[127-0];
RCPPS

格式:RCPPS xmm1, xmm2/m128

功能:求倒数的近似值

算法:

DEST[31-0] = APPROX (1.0/(SRC/m128[31-0])) ;
DEST[63-32] = APPROX (1.0/(SRC/m128[63-32])) ;
DEST[95-64] = APPROX (1.0/(SRC/m128[95-64])) ;
DEST[127-96] = APPROX (1.0/(SRC/m128[127-96]));

RCPSS

格式:RCPSS xmm1, xmm2/m32

功能:求最低位的倒数的近似值

算法:

DEST[31-0] = APPROX (1.0/(SRC/m32[31-0]));
DEST[63-32] = DEST[63-32] ;
DEST[95-64] = DEST[95-64] ;
DEST[127-96] = DEST[127-96];

RSQRTPS

格式:RSQRTPS xmm1, xmm2/m128

功能:求倒数平方根的近似值

算法:

DEST[31-0] = APPROX (1.0/SQRT(SRC/m128[31-0])) ;
DEST[63-32] = APPROX (1.0/SQRT(SRC/m128[63-32])) ;
DEST[95-64] = APPROX (1.0/SQRT(SRC/m128[95-64])) ;
DEST[127-96] = APPROX (1.0/SQRT(SRC/m128[127-96]));

RSQRTSS

格式:RSQRTSS xmm1, xmm2/m32

功能:求最低位倒数平方根的近似值

算法:

DEST[31-0] = APPROX (1.0/SQRT(SRC/m32[31-0]));
DEST[63-32] = DEST[63-32] ;
DEST[95-64] = DEST[95-64] ;
DEST[127-96] = DEST[127-96];

SHUFPS

格式:SHUFPS xmm1, xmm2/m128, imm8

功能:打乱顺序

算法:

FP_SELECT = (imm8 >> 0) AND 0X3;
IF (FP_SELECT = 0) THEN
 DEST[31-0] = DEST[31-0];
ELSEIF (FP_SELECT = 1) THEN
 DEST[31-0] = DEST[63-32];
ELSEIF (FP_SELECT = 2) THEN
 DEST[31-0] = DEST[95-64];
ELSE
 DEST[31-0] = DEST[127-96];
FI

FP_SELECT = (imm8 >> 2) AND 0X3;
IF (FP_SELECT = 0) THEN
 DEST[63-32] = DEST[31-0];
ELSEIF (FP_SELECT = 1) THEN
 DEST[63-32] = DEST[63-32];
ELSEIF (FP_SELECT = 2) THEN
 DEST[63-32] = DEST[95-64];
ELSE
 DEST[63-32] = DEST[127-96];
FI

FP_SELECT = (imm8 >> 4) AND 0X3;
IF (FP_SELECT = 0) THEN
 DEST[95-64] = SRC/m128[31-0];
ELSEIF (FP_SELECT = 1) THEN
 DEST[95-64] = SRC/m128 [63-32];
ELSEIF (FP_SELECT = 2) THEN
 DEST[95-64] = SRC/m128 [95-64];
ELSE
 DEST[95-64] = SRC/m128 [127-96];
FI

FP_SELECT = (imm8 >> 6) AND 0X3;
IF (FP_SELECT = 0) THEN
 DEST[127-96] = SRC/m128 [31-0];
ELSEIF (FP_SELECT = 1) THEN
 DEST[127-96] = SRC/m128 [63-32];
ELSEIF (FP_SELECT = 2) THEN
 DEST[127-96] = SRC/m128 [95-64];
ELSE
 DEST[127-96] = SRC/m128 [127-96];
FI

SQRTPS

格式:SQRTPS xmm1, xmm2/m128

功能:求平方根

算法:

DEST[31-0] = SQRT (SRC/m128[31-0] );
DEST[63-32] = SQRT (SRC/m128[63-32]);
DEST[95-64] = SQRT (SRC/m128[95-64]);
DEST[127-96] = SQRT (SRC/m128[127-96]);

SQRTSS

格式:SQRTSS xmm1, xmm2/m32

功能:最低位数求平方根

算法:

DEST[31-0] = SQRT (SRC/m32[31-0]);
DEST[63-32] = DEST[63-32];
DEST[95-64] = DEST[95-64];
DEST[127-96] = DEST[127-96];

STMXCSR

格式:STMXCSR m32

功能:存储SSE控制字

算法:

m32 = MXCSR;

SUBPS

格式:SUBPS xmm1, xmm2/m128

功能:单精度数的减法运算

算法:

DEST[31-0] = DEST[31-0] - SRC/m128[31-0] ;
DEST[63-32] = DEST[63-32] - SRC/m128[63-32];
DEST[95-64] = DEST[95-64] - SRC/m128[95-64];
DEST[127-96] = DEST[127-96] - SRC/m128[127-96];

SUBSS

格式:SUBSS xmm1, xmm2/m32

功能:最低位数相减

算法:

DEST[31-0] = DEST[31-0] - SRC/m32[31-0];
DEST[63-32] = DEST[63-32];
DEST[95-64] = DEST[95-64];
DEST[127-96] = DEST[127-96];

UCOMISS

格式:UCOMISS xmm1, xmm2/m32

功能:比较低位数并且设置标志位

算法:

OF = 0;
SF = 0;
AF = 0;
IF ((DEST[31-0] UNORD SRC/m32[31-0]) = TRUE) THEN
 ZF = 1;
 PF = 1;
 CF = 1;
ELSEIF ((DEST[31-0] GTRTHAN SRC/m32[31-0]) = TRUE)THEN
 ZF = 0;
 PF = 0;
 CF = 0;
ELSEIF ((DEST[31-0] LESSTHAN SRC/m32[31-0]) = TRUE THEN
 ZF = 0;
 PF = 0;
 CF = 1;
ELSE
 ZF = 1;
 PF = 0;
 CF = 0;
FI

UNPCKHPS

格式:UNPCKHPS xmm1, xmm2/m128

功能:高位两数交替传输

算法:

DEST[31-0] = DEST[95-64];
DEST[63-32] = SRC/m128[95-64];
DEST[95-64] = DEST[127-96];
DEST[127-96] = SRC/m128[127-96];

UNPCKLPS

格式:UNPCKLPS xmm1, xmm2/m128

功能:低位两数交替传输

算法:

DEST[31-0] = DEST[31-0];
DEST[63-32] = SRC/m128[31-0];
DEST[95-64] = DEST[63-32];
DEST[127-96] = SRC/m128[63-32];

XORPS

格式:XORPS xmm1, xmm2/m128

功能:异或运算

算法:

DEST[127-0] = DEST/m128[127-0] XOR SRC/m128[127-0]

OpenCV图像数据结构优化:MMX与SSE技术实现图像反色算法 在图像处理和计算机视觉领域,OpenCV是一个不可或缺的工具库,而Mat是其核心的数据结构。OpenCV由英特尔实验室发起,旨在促进计算机视觉技术的普及和加速开发进程。随着技术的发展,OpenCV逐渐被全球开发者广泛使用,应用于多种领域如安全监控、医疗成像、机器人视觉等。1.1 OpenCV的起源和发展OpenCV(Open Source Computer Vision Library)是一个开源的计算机视觉和机器学习软件库。 阅读详情

相关推荐

基于C++的图像处理算法实现、INTEL上SSE加速、ARM上NEON加速

图像处理算法实现、INTEL上SSE加速、ARM上NEON加速 1.常用图像处理算子实现 2.常用图像处理算子基于Arm 指令集Neon的实现 3.常用图像处理算子基于intel 指令集SSE的实现

fpu, mmx及sse的一些 介绍(原创)

为什么要需要FPU和MMX/SSE?提供了SIMD环境(single instruction multi data),即单指令多数据。内嵌浮点运算单元,64及128位寄存器等。甚至sin/cos等数学函数也囊括其中,著名的xvid项目就是使用gcc编译后使用MMX/SSE优化汇编的典型案例。转载请注明原创:http://www.cppblog.com/jinglexy,现在使用博客:http://

拥剑的博客 1204

王爽《汇编语言》课程设计2(不涉及软盘版本)

assume cs:code,ds:data,ss:stack stack segment db 128 dup (0) stack ends data segment db 256 dup (0) data ends code segment start: mov ax,stack mov ss,ax mov sp,128 ...

weixin_41944412的博客 1178

ClickHouse为什么这么快(二)SSE指令优化

通过SIMD指令优化数据统计性能

zhangqhn的博客 644

保姆级教程:用CH34xSerCfg工具修改USB转串口芯片的VID/PID,避免驱动冲突

本文详细介绍了如何使用CH34xSerCfg工具修改USB转串口芯片的VID/PID,解决驱动冲突问题。通过实战案例和配置技巧,帮助开发者高效管理嵌入式设备,避免常见的USB设备识别问题,提升开发效率。

weixin_30924239的博客 224

Python爬虫实战:5分钟搞定Web of Science文献批量导出与解析(附完整代码)

本文提供了一套利用Python爬虫技术,快速实现Web of Science文献批量提取与解析的完整方案。通过解析官方导出的HTML文件,结合BeautifulSoup和pandas库,可将文献数据自动转换为结构化的Excel/CSV表格,帮助科研人员高效管理文献信息,节省大量手动整理时间。

weixin_29050513的博客 1164

指令集简介

SIMD(Single Instruction Multiple Data)是单指令多数据技术,目前Intel处理器支持的SIMD技术包括MMX,SSE,AVX。SSE(Stream SIMD Extentions,数据流单指令多数据扩展)是英特尔继MMX(Multi Media eXtension,多媒体扩展指令集)之后推出的新一代CPU指令集。MMX提供了8个64bit的寄存器进行SIMD操作,SSE系列提供了8个128bit的寄存器进行SIMD操作。

贾路飞的博客 2万+

FR4板材实战:用ADS 2023快速设计微带线低通滤波器(附Line-Cal计算技巧)

本文详细介绍了使用ADS 2023在FR4板材上设计1-3GHz微带线低通滤波器的工程技巧。通过Line-Cal工具快速计算微带线参数,解决FR4板材的介质损耗和阻抗匹配问题,提供从集总参数转换到分布参数的实用方法,并分享版图设计与实测验证的关键要点,帮助工程师高效完成射频滤波器设计。

omega的博客 713

使用SSE指令集来优化程序

SSE和SSE2的指令系统非常相似,SSE2比SSE多的仅是少量的额外浮点处理功能、64位浮点数运算支持和64位整数运算支持。 SSE为什么会比传统的浮点运算更快呢?因为它使用了128位的存储单元,这对于32位的浮点数来讲,是可以存下4个的,也就是说,SSE中的所有计算都是一次性针对4个浮点数来完成的。 虽然SSE从理论上来讲要比传统的浮点运算会快,但是所受的限制也很多,首先,虽然它执行一次相当于四次,会比传统的浮点运算执行4次的速度要快,但是它执行一次的速度却并没有想象中的那...

百里杨的博客 4914

高缺失率时空数据插补实战:从随机森林到扩散模型的性能对比

数据缺失是数据分析与机器学习建模中普遍面临的挑战,尤其在时空数据领域,传感器故障、传输中断等问题常导致数据不完整。数据插补技术旨在基于已知数据的模式和关联性,合理估算缺失值,为后续分析提供可靠基础。其核心原理在于利用数据的时空相关性(如时间周期性、空间邻近性)及与外部驱动因素(如交通、气象)的关联构建预测模型。这项技术的价值在于能将不完整的数据集转化为可用于高质量分析和预测的可用资产,广泛应用于环境监测、交通流量预测、金融风控等领域。本文聚焦于一个极具挑战性的场景——PM2.5监测数据缺失率高达82%,通过

weixin_30363285的博客 544

Python从0到100完整学习指南(必看导航)

想做这件事情很久了,这次我更新了自己所写过的所有博客,汇集成了Python从0到100,共一百节课,帮助大家一个月时间里从零基础到学习Python基础语法、Python爬虫、Web开发、 计算机视觉、机器学习、神经网络以及人工智能相关知识,成为学业升学和工作就业的先行者!

拥有百余位万粉技术博主、200余位可合作代发博主,私域技术社群规模达千人,商务合作私信 6万+

SSE 指令

SSE指令

少年的此间 3820

【深度学习新浪潮】什么是system 1和system 2?

System 1(快速生成)指大模型直接基于输入生成响应,无需显式中间推理步骤。例如,GPT-4等模型在默认状态下通过Transformer直接输出结果,擅长快速回答简单问题或生成连贯文本,但在复杂逻辑任务中可能出错。这类模型的内部计算以向量形式隐式进行,难以处理符号推理等需要离散决策的任务。System 2(慢速推理)指模型通过生成中间token(如思维链、分步推导)或多次调用LLM进行复杂推理。

专注:太空算力、AI infra、异构调度、大模型成本工程 924

MMX及SSE优化--MMX篇

MMX和SSE都是INTEL开发的基于SIMD(单指令多数据流)的技术。所谓单指令多数据流是指可以用一条指令可以完成多个数据的操作。虽然64位系统已经推出,但是我们大部分都是使用32位系统,所以如果要完成两个128位的相加运算,用普通32位指令很明显要执行4条相加指令,而基于64位的MMX指令只需要执行两次即可完成,更强大的SSE能一次处理128位,故一次就可以完成操作,所以采用MMX及SSE优化

feixiaku的专栏 1178

有效Dk值提取方法的仿真分析

通过本文的仿真对比分析,提取有效Dk值方面,TDR技术在一些固定的场景下,依然有其参考应用价值,而随着VNA功能的不断增强和高精度测量手段的不断更新,双端口Delta-L技术才是主流评估方法,而单端口Delta-L技术则可以作为其降本增效的方案补充。

一只豌豆象的博客 1823

计算机控制技术及应用

《计算机控制技术及应用》通过总结作者的科研成果和吸收国内外的先进理论、方法和技术,以计算机控制系统的网络化、开放化、智能化和集成化发展趋势为主线索,主要介绍计算机控制系统的基本概念和计算机控制系统的典型形式,计算机控制系统的数学描述与基本分析方法,以及数字PID控制器、最少拍控制系统、达林算法、状态变量设计法等设计方法及其各种改进算法。重点突出计算机控制系统输入输出通道接口的设计方法和典型控制系统的设计案例与实现方法等。

c语言评价函数,自己编写的strlen函数 各位评价分析下

该楼层疑似违规已被系统折叠隐藏此楼查看此楼全角 换 掉-----------------------static __declspec(naked) void great_ansi_counter(const char*){__asm{mov     eax,dword ptr[esp+4] ; source_pointer to poll (will increase)mov     ebx,...

weixin_28366053的博客 116

win10 跳过U8环境检测的IE WebControls.rar

win10 安装u8的时候 提示IE WebControls 不通过,这个工具可以欺骗u8的检查。 跳过U8环境检测的IE WebControls。提示导入失败后,重新检测通过。

计算机英语术语介绍,计算机英语术语大全.doc

计算机英语术语大全.doc1、CPU3DNow!(3D no waiting)ALU(Arithmetic Logic Unit,算术逻辑单元)AGU(Address Generation Units,地址产成单元)BGA(Ball Grid Array,球状矩阵排列)BHT(branch prediction table,分支预测表)BPU(Branch Processing Unit,分支处理...

weixin_31080131的博客 199

VB摄像头监控

该VB模块可对摄像头捕获的画面进行录像等,可在创建的窗口进行控制

文档:亲测可用解决vnc灰屏,黑屏,鼠标大黑叉情况

主要解决vnc-viewer灰屏,黑屏,鼠标大黑叉等现象,详细见文档。

关于使用MMX/SSE技术优化memcpy的尝试

近来,希望能通过使用某种技术优化常规memcpy()的性能,于是尝试了 MMX/SSE,希望能借此实现一个性能更高的memcpy函数。代码如下(里面的USE2函数是借用别人的,但性能也不怎么样):#include #include #include #include #include #define LEN 100*1024*1024 #define USE1 class TimeUse{ public: TimeUse(char * cMsg) { mem

OJOE的专栏 7573

MMX,SSE,SSE2扫盲

MMX 指令集 MMX(Multi Media eXtension,多媒体扩展指令集)指令集是Intel公司于1996年推出的一项多媒体指令增强技术。MMX指令集中包括有57条多媒体指令, 通过这些指令可以一次处理多个数据,在处理结果超过实际处理能力的时候也能进行正常处理,这样在软件的配合下,就可以得到更高的性能。MMX的益处在于, 当时存在的操作系统不必为此而做出任何修改便可以轻松地

兼容并蓄终宽阔,若谷虚怀鱼自游 7816

【整理】SIMD、MMX、SSE、AVX、3D Now!、neon

SIMD SIMD单指令流多数据流(SingleInstruction Multiple Data,SIMD)是一种采用一个控制器来控制多个处理器,同时对一组数据(又称“数据向量”)中的每一个分别执行相同的操作从而实现空间上的并行性的技术。在微处理器中,单指令流多数据流技术则是一个控制器控制多个平行的处理微元,例如Intel的MMX或SSE以及AMD的3D Now!技术。 --------

[conowen]大钟的专栏 3万+

MMX和SSE的运用

Intel的MM技术是对Intel体系结构(IA)指令集的扩展。该技术使用了单指令多数据技术(SIMD)技术,以并行方式处理多个数据元素。MMX?指令集增加了57条新的操作码和一个新的64位四字数据类型,增加了八个新的64位MMX寄存器,每个寄存器可按名称MM0-MM7直接访问。这意味着我们可以在一个寄存器里最多存8个数据(最小单位字节)。  SSE系列是MMX的超集,直到SSE2才跟MMX有本

feixiaku的专栏 1532
上一篇: MMX及SSE优化--MMX篇
下一篇: 再谈MMX优化
dbgnu
博客等级 码龄25年 3粉丝 3原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值