请问如何给一个数组初始化全部相同的值?

qq_22305005 2016-12-16 10:14:14
比如数组a[1000],我想一次全部给赋值11111;有没有简单的办法?
...全文
2098 61 打赏 收藏 转发到动态 举报
写回复
用AI写文章
61 条回复
切换为时间正序
请发表友善的回复…
发表回复
赵4老师 2016-12-23
  • 打赏
  • 举报
回复
void HexDump(char *buf,int len,int addr) {
    int i,j,k;
    char binstr[80];

    for (i=0;i<len;i++) {
        if (0==(i%16)) {
            sprintf(binstr,"%08x -",i+addr);
            sprintf(binstr,"%s %02x",binstr,(unsigned char)buf[i]);
        } else if (15==(i%16)) {
            sprintf(binstr,"%s %02x",binstr,(unsigned char)buf[i]);
            sprintf(binstr,"%s  ",binstr);
            for (j=i-15;j<=i;j++) {
                sprintf(binstr,"%s%c",binstr,('!'<buf[j]&&buf[j]<='~')?buf[j]:'.');
            }
            printf("%s\n",binstr);
        } else {
            sprintf(binstr,"%s %02x",binstr,(unsigned char)buf[i]);
        }
    }
    if (0!=(i%16)) {
        k=16-(i%16);
        for (j=0;j<k;j++) {
            sprintf(binstr,"%s   ",binstr);
        }
        sprintf(binstr,"%s  ",binstr);
        k=16-k;
        for (j=i-k;j<i;j++) {
            sprintf(binstr,"%s%c",binstr,('!'<buf[j]&&buf[j]<='~')?buf[j]:'.');
        }
        printf("%s\n",binstr);
    }
}
赵4老师 2016-12-23
  • 打赏
  • 举报
回复
电脑内存或文件内容或传输内容只是一个一维二进制字节数组及其对应的二进制地址; 人脑才将电脑内存或文件内容或传输内容中的这个一维二进制字节数组及其对应的二进制地址的某些部分看成是整数、有符号数/无符号数、浮点数、复数、英文字母、阿拉伯数字、中文/韩文/法文……字符/字符串、汇编指令、函数、函数参数、堆、栈、数组、指针、数组指针、指针数组、数组的数组、指针的指针、二维数组、字符点阵、字符笔画的坐标、黑白二值图片、灰度图片、彩色图片、录音、视频、指纹信息、身份证信息…… 推荐使用WinHex软件查看硬盘或文件或内存中的原始字节内容。
AlbertS 2016-12-22
  • 打赏
  • 举报
回复
	
memset(a,1,sizeof(a))
AlbertS 2016-12-22
  • 打赏
  • 举报
回复
memset(a,1,sizeof(a)
AlbertS 2016-12-22
  • 打赏
  • 举报
回复
memset(a,1,sizeof(a)
赵4老师 2016-12-22
  • 打赏
  • 举报
回复
引用 55 楼 DelphiGuy 的回复:
编译器的优化水平和人工比还是有差距(当然不是随便什么人)。
#include <windows.h>
//#include <intrin.h>
#include <stdio.h>
#define COUNT 8000
__declspec(align(16)) float data[COUNT];
int i;
unsigned __int64 nCtr2,nCtr1;
int main() {
//  for (i=0;i<COUNT;i++) {data[i]=1.0f;printf("%g\n",data[i]);}

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        push edi
        mov ecx,COUNT
        mov eax,0xBF800000 //-1.0f
        lea edi,data
        rep stosd
        pop edi
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        mov eax,0xBF800000 //-1.0f
        mov ecx,COUNT/80
        movd xmm0,eax
        lea eax,data
        pshufd xmm0,xmm0,0
    __loop:
        movdqa [eax+64],xmm0
        movdqa [eax+48],xmm0
        movdqa [eax+32],xmm0
        movdqa [eax+16],xmm0
        movdqa [eax],xmm0
        add eax,80
        sub ecx,1
        jnz __loop
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
//  data[0]=-1.0f;
//  __m128 m128=_mm_load_ps1((float *)&data[0]);
//  for (i=0;i<COUNT;i+=4) _mm_store_ps1(&data[i],m128);
    __asm {
        push ecx
        mov eax,0xBF800000 //-1.0f
        movd xmm0,eax
        shufps xmm0,xmm0,0
        lea eax,data
        mov ecx,eax
        add ecx,COUNT*4 //COUNT*sizeof(float)
    loop1:
        movaps oword ptr [eax],xmm0
        add eax,16
        cmp eax,ecx
        jb loop1
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

//  for (i=0;i<COUNT;i++) printf("%g\n",data[i]);

    return 0;
}
//36679
//2228
//4806
//
  • 打赏
  • 举报
回复
编译器的优化水平和人工比还是有差距(当然不是随便什么人)。
  • 打赏
  • 举报
回复
换成你复制出来的汇编代码也不行,大致是这样的差距: 18639 1329 4152
  • 打赏
  • 举报
回复
这个是使用对齐指令的代码,建议你找一个新一点的机器测试:


#include <stdio.h>
#include <windows.h>
#include <intrin.h>

#define COUNT 5000000
__declspec(align(16)) float data[COUNT];

unsigned __int64 nCtr2,nCtr1;
int main() {
//  for (i=0;i<COUNT;i++) {data[i]=1.0f;printf("%g\n",data[i]);}
 
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push edi
        mov ecx,COUNT
        mov eax,0xBF800000 //-1.0f
        lea edi,data
        rep stosd
        pop edi
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);
 
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        mov eax,0xBF800000 //-1.0f
        mov ecx,COUNT /80
        movd xmm0,eax
        lea eax,data
        pshufd xmm0,xmm0,0
    __loop:
        movdqa [eax+64],xmm0
        movdqa [eax+48],xmm0
        movdqa [eax+32],xmm0
        movdqa [eax+16],xmm0
        movdqa [eax],xmm0
        add eax,80
        sub ecx,1
        jnz __loop
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);
 
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    data[0]=-1.0f;
    __m128 m128=_mm_load_ps1((float *)&data[0]);
    for (int i=0;i<COUNT;i+=4) _mm_store_ps1(&data[i],m128);
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);
 
//  for (i=0;i<COUNT;i++) printf("%g\n",data[i]);
 
    return 0;
}
赵4老师 2016-12-22
  • 打赏
  • 举报
回复
纠正49楼第三段汇编代码后:
#include <windows.h>
//#include <intrin.h>
#include <stdio.h>
__declspec(align(16)) float data[500];
int i;
unsigned __int64 nCtr2,nCtr1;
int main() {
//  for (i=0;i<500;i++) {data[i]=1.0f;printf("%g\n",data[i]);}

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        push edi
        mov ecx,500
        mov eax,0xBF800000 //-1.0f
        lea edi,data
        rep stosd
        pop edi
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        push edi
        mov eax,0xBF800000 //-1.0f
        mov ecx,25
        movd xmm0,eax
        lea edi,data
        pshufd xmm0,xmm0,0
    __loop:
        movdqu [edi+64],xmm0
        movdqu [edi+48],xmm0
        movdqu [edi+32],xmm0
        movdqu [edi+16],xmm0
        movdqu [edi],xmm0
        add edi,80
        sub ecx,1
        jnz __loop
        pop edi
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
//  data[0]=-1.0f;
//  __m128 m128=_mm_load_ps1((float *)&data[0]);
//  for (i=0;i<500;i+=4) _mm_store_ps1(&data[i],m128);
    __asm {
        push ecx
        mov eax,0xBF800000 //-1.0f
        movd xmm0,eax
        shufps xmm0,xmm0,0
        lea eax,data
        mov ecx,eax
        add ecx,500*4 //500*sizeof(float)
    loop1:
        movaps oword ptr [eax],xmm0
        add eax,16
        cmp eax,ecx
        jl loop1
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

//  for (i=0;i<500;i++) printf("%g\n",data[i]);

    return 0;
}
//824
//1107
//648
//
  • 打赏
  • 举报
回复
1. i没有赋初值 2. cmp eax,ecx逻辑错误 另外,你强制数据16字节对齐了,当然可以使用更快的对齐操作指令movaps、movdqa之类的
赵4老师 2016-12-22
  • 打赏
  • 举报
回复
发现楼上第三段汇编代码逻辑有错误。
赵4老师 2016-12-22
  • 打赏
  • 举报
回复
#include <windows.h>
//#include <intrin.h>
#include <stdio.h>
__declspec(align(16)) float data[500];
int i;
unsigned __int64 nCtr2,nCtr1;
int main() {
//  for (i=0;i<500;i++) {data[i]=1.0f;printf("%g\n",data[i]);}

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        push edi
        mov ecx,500
        mov eax,0xBF800000 //-1.0f
        lea edi,data
        rep stosd
        pop edi
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        push edi
        mov eax,0xBF800000 //-1.0f
        mov ecx,25
        movd xmm0,eax
        lea edi,data
        pshufd xmm0,xmm0,0
    __loop:
        movdqu [edi+64],xmm0
        movdqu [edi+48],xmm0
        movdqu [edi+32],xmm0
        movdqu [edi+16],xmm0
        movdqu [edi],xmm0
        add edi,80
        sub ecx,1
        jnz __loop
        pop edi
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
//  data[0]=-1.0f;
//  __m128 m128=_mm_load_ps1((float *)&data[0]);
//  for (i=0;i<500;i+=4) _mm_store_ps1(&data[i],m128);
    __asm {
        push ecx
        mov eax,0xBF800000 //-1.0f
        movd xmm0,eax
        shufps xmm0,xmm0,0
        lea eax,data
        mov ecx,i
    loop1:
        movaps oword ptr [eax],xmm0
        add eax,16
        cmp eax,ecx
        jl loop1
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

//  for (i=0;i<500;i++) printf("%g\n",data[i]);

    return 0;
}
//796
//1107
//499
//
PixelDemon 2016-12-22
  • 打赏
  • 举报
回复
memset只能对字节类型数据统一赋值,这个你们都不知道吗。 对于其他类型,除非是特殊数字(比如0),否则无法利用memset
赵4老师 2016-12-22
  • 打赏
  • 举报
回复
最新研究成果:
#include <windows.h>
#include <intrin.h>
#include <stdio.h>
__declspec(align(16)) float data[500];
int i;
unsigned __int64 nCtr2,nCtr1;
int main() {
//  for (i=0;i<500;i++) {data[i]=1.0f;printf("%g\n",data[i]);}

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        push edi
        mov ecx,500
        mov eax,0xBF800000 //-1.0f
        lea edi,data
        rep stosd
        pop edi
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        push edi
        mov eax,0xBF800000 //-1.0f
        mov ecx,25
        movd xmm0,eax
        lea edi,data
        pshufd xmm0,xmm0,0
__loop:
        movdqu [edi+64],xmm0
        movdqu [edi+48],xmm0
        movdqu [edi+32],xmm0
        movdqu [edi+16],xmm0
        movdqu [edi],xmm0
        add edi,80
        sub ecx,1
        jnz __loop
        pop edi
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    data[0]=-1.0f;
    __m128 m128=_mm_load_ps1((float *)&data[0]);
    for (i=0;i<500;i+=4) _mm_store_ps1(&data[i],m128);
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

//  for (i=0;i<500;i++) printf("%g\n",data[i]);

    return 0;
}
//837
//1067
//823
//
版主是不是该加精啊!
  • 打赏
  • 举报
回复
引用 25 楼 zhao4zhong1 的回复:
在强势地问一句,为什么下面代码的执行结果显示还是rep stosd快呢?!
#include <windows.h>
#include <stdio.h>
float data[500];
int i;
unsigned __int64 nCtr2,nCtr1;
int main() {
//  for (i=0;i<500;i++) {data[i]=1.0f;printf("%g\n",data[i]);}

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        push edi
        mov ecx,500
        mov eax,0xBF800000 //-1.0f
        lea edi,data
        rep stosd
        pop edi
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        push edi
        mov eax,0xBF800000 //-1.0f
        mov ecx,25
        movd xmm0,eax
        lea edi,data
        pshufd xmm0,xmm0,0
__loop:
        movdqu [edi+64],xmm0
        movdqu [edi+48],xmm0
        movdqu [edi+32],xmm0
        movdqu [edi+16],xmm0
        movdqu [edi],xmm0
        add edi,80
        sub ecx,1
        jnz __loop
        pop edi
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

//  for (i=0;i<500;i++) printf("%g\n",data[i]);

    return 0;
}
//837
//2592
//
不要迷信书、考题、老师、回帖; 要迷信CPU、编译器、调试器、运行结果。 并请结合“盲人摸太阳”和“驾船出海时一定只带一个指南针。”加以理解。 任何理论、权威、传说、真理、标准、解释、想象、知识……都比不上摆在眼前的事实!
你的是虚拟机?不可能连SSE2都不支持,是仿真的吧。 我的测试: 数组元素数量500,结果是0 0,加大到50000,结果 164 26,加大到5000000,结果18380 5279。由于代码只执行一次,有些波动,大致如此。 CPU:i7-6700k 编译器:用于 x86 的 Microsoft (R) C/C++ 优化编译器 19.00.24210 版 (没有用64位编译器,ms的64位编译器不支持内嵌汇编,如果用intel C++64位编译要修改程序,基于edi的32位寻址都要改成64位寻址)
赵4老师 2016-12-21
  • 打赏
  • 举报
回复
引用 27 楼 Dobzhansky 的回复:
围观,看不懂汇编
“扮猪吃老虎”了吧。 计算机组成原理→DOS命令→汇编语言→C语言(不包括C++)、代码书写规范→数据结构、编译原理、操作系统→计算机网络、数据库原理、正则表达式→其它语言(包括C++)、架构……
Dobzhansky 2016-12-21
  • 打赏
  • 举报
回复
围观,看不懂汇编
赵4老师 2016-12-21
  • 打赏
  • 举报
回复
强势……
赵4老师 2016-12-21
  • 打赏
  • 举报
回复
在强势地问一句,为什么下面代码的执行结果显示还是rep stosd快呢?!
#include <windows.h>
#include <stdio.h>
float data[500];
int i;
unsigned __int64 nCtr2,nCtr1;
int main() {
//  for (i=0;i<500;i++) {data[i]=1.0f;printf("%g\n",data[i]);}

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        push edi
        mov ecx,500
        mov eax,0xBF800000 //-1.0f
        lea edi,data
        rep stosd
        pop edi
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr1);
    __asm {
        push ecx
        push edi
        mov eax,0xBF800000 //-1.0f
        mov ecx,25
        movd xmm0,eax
        lea edi,data
        pshufd xmm0,xmm0,0
__loop:
        movdqu [edi+64],xmm0
        movdqu [edi+48],xmm0
        movdqu [edi+32],xmm0
        movdqu [edi+16],xmm0
        movdqu [edi],xmm0
        add edi,80
        sub ecx,1
        jnz __loop
        pop edi
        pop ecx
    }
    QueryPerformanceCounter((LARGE_INTEGER *) &nCtr2);
    printf("%I64u\n",nCtr2-nCtr1);

//  for (i=0;i<500;i++) printf("%g\n",data[i]);

    return 0;
}
//837
//2592
//
不要迷信书、考题、老师、回帖; 要迷信CPU、编译器、调试器、运行结果。 并请结合“盲人摸太阳”和“驾船出海时一定只带一个指南针。”加以理解。 任何理论、权威、传说、真理、标准、解释、想象、知识……都比不上摆在眼前的事实!
加载更多回复(41)

64,637

社区成员

发帖
与我相关
我的任务
社区描述
C++ 语言相关问题讨论,技术干货分享,前沿动态等
c++ 技术论坛(原bbs)
社区管理员
  • C++ 语言社区
  • encoderlee
  • paschen
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
  1. 请不要发布与C++技术无关的贴子
  2. 请不要发布与技术无关的招聘、广告的帖子
  3. 请尽可能的描述清楚你的问题,如果涉及到代码请尽可能的格式化一下

试试用AI创作助手写篇文章吧