C++嵌入彙編語言計算有符號數組的平均值

  • 2019 年 11 月 7 日
  • 筆記

版權聲明:本文為部落客原創文章,遵循 CC 4.0 BY-SA 版權協議,轉載請附上原文出處鏈接和本聲明。

本文鏈接:https://blog.csdn.net/weixin_42449444/article/details/102556037

關於嵌入彙編:

嵌入彙編是指在C和C++的源程式中插入彙編語言指令,也稱內嵌彙編、內聯彙編或行內彙編。VisualC++中使用「__asm」關鍵字指示嵌入彙編,不需要獨立的彙編系統就可以正常編譯和連接。使用「__asm」關鍵字既可以引導單條回彙編語言指令,也可以用空格在同一行分隔多個「__asm」引導的彙編語言指令,更好的方法是使用花括弧書寫一個彙編語言程式片段。

VC++6.0支援通用整數和浮點指令集以及MMX指令集的嵌入彙編。對於還不能支援的指令,VC++提供了_emit偽指令進行拓展。嵌入彙編語言程式碼可以使用C++的數據類型和數據對象,也可以使用MASM的表達式和注釋風格,但不可以使用MASM的絕大多數偽指令和宏彙編方法。

在VC++中使用嵌入彙編還需要注意一些具體的規定。例如,在彙編語言編寫的函數中,不必保存EAX、EBX、ECX、EDX、ESI和EDI暫存器,但必須保存函數中使用的其它暫存器(如ESP、EBP和整數標誌暫存器等)。嵌入式彙編語言語句中,可以使用彙編語言格式表示整數常量(如378H),也可以使用C++的格式來進行表示(如0x378)。嵌入式彙編中的標號和C++的標號相似,它的作用是在定義它的函數中有效。

在VC++集成開發環境中,建立一個win32控制台程式的項目,輸入源程式碼後進行編譯連接就可以產生一個可執行文件。需要注意的是:debug活動解決方案平台一定要選X86!不能夠X64!不然編譯器會報錯。

計算有符號數組的平均值:

#include <iostream>  using namespace std;  #define Up(i,a,b) for(int i = a; i <= b; i++)  const int maxn = 1005;  int getAvg(int d[], int n,int* m);    //嵌入彙編語言來計算有符號數平均值    int main()  {      ios::sync_with_stdio(false);      cin.tie(0), cout.tie(0);      int d[maxn];      int n;    //數組大小n      cin >> n;      Up(i, 0, n - 1)      {          cin >> d[i];      }      int* m = new int;   //餘數m      int avg = getAvg(d, n,m);   //商      cout << "平均值是:" << avg << endl;      if (*m != 0)      {          cout << "餘數是:" << *m << endl;      }      delete m;   //刪除指針並置為空      m = NULL;      return 0;  }    int getAvg(int d[], int n,int* m)  {      int avg,rmd;   //平均值avg,餘數rmd      __asm   //嵌入彙編程式碼      {          mov ebx, d        //EBX=數組地址          mov ecx, n        //ECX=數據個數          xor eax, eax      //EAX保存和,先清零          xor edx, edx      //EDX=當前指向數組元素的下標          getsum :          //循環求數組和          add eax, [ebx + edx * 4]              add edx, 1    //指向下一地址              cmp edx, ecx  //比較當前下標是否小於數據個數n              jb getsum     //繼續循環              cdq           //將累加和EAX符號擴展到EDX          idiv ecx      //有符號除法,EAX=商,EDX=餘數          mov avg, eax  //將EAX的值賦給avg          mov rmd,edx    //將EDX的值賦給*m      }      *m = rmd;    //直接mov *m,edx會有內聯彙編語法錯誤      return avg;  }