如题,
不知道有没有什么现成的函数?
有什么好的资料吗?
先谢谢了
少人是因为你这问题实在没啥意思。
这种问题,在网上搜索一下,有几千个答案。
引用: 引用 4 楼 yashi 的回复:
少人是因为你这问题实在没啥意思。
这种问题,在网上搜索一下,有几千个答案。
----------------------------------
但是那些算法效率太低了,我旋转一个500x400的图片要6,7秒啊,
这么慢远远达不到要求
我想问的是有没有高效的算法
你用函数PlgBlt()你自己看看函数传入的3个POINT点参数不同就可以达到旋转的效果的 不过精确度一般
引用: 引用 7 楼 wh_peng 的回复:
引用 4 楼 yashi 的回复:
少人是因为你这问题实在没啥意思。
这种问题,在网上搜索一下,有几千个答案。
----------------------------------
但是那些算法效率太低了,我旋转一个500x400的图片要6,7秒啊,
这么慢远远达不到要求
我想问的是有没有高效的算法
你的意思是这样吗?那是你懒得把问题写清楚,还是你写了,我没看出来?
引用: 引用 7 楼 wh_peng 的回复:
引用 4 楼 yashi 的回复:
少人是因为你这问题实在没啥意思。
这种问题,在网上搜索一下,有几千个答案。
----------------------------------
但是那些算法效率太低了,我旋转一个500x400的图片要6,7秒啊,
这么慢远远达不到要求
我想问的是有没有高效的算法
算法你自己不会改一下啊,那么小的图,根本不用6,7秒。要点就是采用整数运算。
引用: 引用 10 楼 nbcool 的回复:
引用 7 楼 wh_peng 的回复:
引用 4 楼 yashi 的回复:
少人是因为你这问题实在没啥意思。
这种问题,在网上搜索一下,有几千个答案。
----------------------------------
但是那些算法效率太低了,我旋转一个500x400的图片要6,7秒啊,
这么慢远远达不到要求
我想问的是有没有高效的算法
算法你自己不会改一下啊,那么小的图,根本不用6,7秒。要点就是采用整数运算。
------------------------------------------------------------------
怎样采用整数运算?可以详细点说吗?我不太理解,谢谢了
就是浮点换整数,内存换速度的优化技术,网上到处都是-_-0
1.对于0,90,180,270,360之类的角度,何必再去调用sin cos等函数计算位置?直接用整数值代替就行了,你不觉得调用数字计算比调用函数会快一点吗,何况要调用500x400x3次?
2.类似取sin(1)~sin(360)之类的公式,完全可以用一个360个元素的整数数组替代。浮点可采用近似整数值替代或者用更好的转整数算法。
3.内存操作优化。
4.流水线优化。
5.函数级优化
等等还有很多地方可以优化,没事多看书吧,写软件没看过内存及代码优化技术的书是不行的。
我把NBCOOL老大的话补充说明一下:)你就是用一张有360个元素的表代替SIN COS的运算,比如你求SIN(1)的话就直接查表了,而不是用math.h当中的SIN去算:)然后看下有关的资料是不是并根据相应的情况,看看到底是内存重要还是效率重要。做下优化。
另外提醒一下,尽量不要过于频繁的NEW DELETE,那样内存碎片太多,反而不好。
谢谢 nbcool BEYONDMA
我优化优化看先
经过优化,速度大大提高了,
500*400的图片1秒了,2592*3800的也才3秒左右
再次感谢nbcool BEYONDMA
你发错版了。
正确是 “图形图像/机器视觉删除”或 “VC/MFC删除/图形处理/算法添加”。
图像旋转是很基本的操作,像500*400这种小图像应该在1-3ms之间。
刚才在另一个函数修改的,可能有些错误。
image是原图的数据,newImage是旋转后的图,调用前未分配空间,在Rotate里分配。fRotateAngle是旋转的弧度。
- void Rotate(uchar *image,int width,int height,uchar *&newImage, int &newWidth,int &newHeight, float fRotateAngle)
- {
- // 旋转角度的正弦和余弦
- float fSina, fCosa;
- // 两个中间常量
- float f1,f2;
- // 象素在源DIB中的坐标
- int i0;
- int j0;
- // 源图四个角的坐标(以图像中心为坐标系原点)
- float fSrcX1,fSrcY1,fSrcX2,fSrcY2,fSrcX3,fSrcY3,fSrcX4,fSrcY4;
- // 旋转后四个角的坐标(以图像中心为坐标系原点)
- float fDstX1,fDstY1,fDstX2,fDstY2,fDstX3,fDstY3,fDstX4,fDstY4;
- // 计算旋转角度的正弦
- fSina = (float) sin((double)fRotateAngle);
- // 计算旋转角度的余弦
- fCosa= (float) cos((double)fRotateAngle);
- // 计算原图的四个角的坐标(以图像中心为坐标系原点)
- fSrcX1 = (float) (- (width - 1) / 2);
- fSrcY1 = (float) ( (height - 1) / 2);
- fSrcX2 = (float) ( (width - 1) / 2);
- fSrcY2 = (float) ( (height - 1) / 2);
- fSrcX3 = (float) (- (width - 1) / 2);
- fSrcY3 = (float) (- (height - 1) / 2);
- fSrcX4 = (float) ( (width - 1) / 2);
- fSrcY4 = (float) (- (height - 1) / 2);
- // 计算新图四个角的坐标(以图像中心为坐标系原点)
- fDstX1 = fCosa * fSrcX1 + fSina * fSrcY1;
- fDstY1 = -fSina * fSrcX1 + fCosa * fSrcY1;
- fDstX2 = fCosa * fSrcX2 + fSina * fSrcY2;
- fDstY2 = -fSina * fSrcX2 + fCosa * fSrcY2;
- fDstX3 = fCosa * fSrcX3 + fSina * fSrcY3;
- fDstY3 = -fSina * fSrcX3 + fCosa * fSrcY3;
- fDstX4 = fCosa * fSrcX4 + fSina * fSrcY4;
- fDstY4 = -fSina * fSrcX4 + fCosa * fSrcY4;
- // 计算旋转后的图像实际宽度
- newWidth = (int) ( max( fabs(fDstX4 - fDstX1), fabs(fDstX3 - fDstX2) ) + 0.5);
- // 计算旋转后的图像高度
- newHeight = (int) ( max( fabs(fDstY4 - fDstY1), fabs(fDstY3 - fDstY2) ) + 0.5);
- //int length= newWidth* newHeight;
- newImage=new uchar[ newWidth* newHeight];
- // 两个常数,这样不用以后每次都计算了
- f1 = (float) (-0.5 * (newWidth - 1) * fCosa - 0.5 * (newHeight - 1) * fSina
- + 0.5 * (width - 1));
- f2 = (float) ( 0.5 * (newWidth - 1) * fSina - 0.5 * (newHeight - 1) * fCosa
- + 0.5 * (height - 1));
- // 针对图像每行进行操作
- for(int i = 0; i < newHeight; i++)
- {
- // 针对图像每列进行操作
- for(int j = 0; j < newWidth; j++)
- {
- // 计算该象素在源DIB中的坐标
- i0 = int(-((float) j) * fSina + ((float) i) * fCosa + f2+0.5);
- j0 = int(((float) j) * fCosa + ((float) i) * fSina + f1+0.5);
- if( (i0 < 0) || (j0 > width - 1) || (j0 < 0) || (i0 > height - 1))
- {
- // 要计算的点不在源图范围内,直接返回255。
- newImage[newWidth*(i)+j]=255;
- }
- else
- newImage[newWidth* (i) +j]=image[width*(i0)+j0];
- }
- }
- }