1.マクロのオフセット
まず、offsetof マクロが何であるかを理解する必要があります。
関数形式のこのマクロは、データ構造または共用体型のメンバー メンバーのオフセット値をバイト単位で返します。
戻り値は、指定されたメンバーとその構造体の先頭の間のバイト数を含む、size_t 型の符号なし整数値です。
それは何を意味しますか? 以下の図をご覧ください:
この演習を見てみましょう:
演習の内容:
最初のアドレスを基準とした構造体の変数のオフセットを計算するマクロを作成します。
問題解決のアイデア:
質問の意味によると、最初にマクロ OFFSETOF を定義する必要があります。開始位置に対するメンバー変数のオフセットを返したいので、構造体名とメンバー変数を渡す必要があります。名前; では、オフセットを計算するにはどうすればよいですか
? ?
開始アドレスを 0x00000000 として取得し、メンバー変数のアドレスを返すと、結果がオフセットになります。
コードデモ:
#include<stdio.h>
#define OFFSETOF(STN,MEN) (int)&(((struct S*)0)->MEN)
typedef struct S
{
int a;
char b;
char c;
int d;
}node;
int main()
{
printf("%d\n", OFFSETOF(node S, a));
printf("%d\n", OFFSETOF(node S, b));
printf("%d\n", OFFSETOF(node S, c));
printf("%d\n", OFFSETOF(node S, d));
return 0;
}
}
出力結果:
解析:
2. パリティビットを交換する
演習の内容:
整数の 2 進数の奇数ビットと偶数ビットを交換できるマクロを作成します。
問題解決のアイデア:
質問の意味によると、最初にマクロ EXCHANGE を定義し、交換する変数の名前を渡す必要があります。
奇数ビットと偶数ビットを交換する必要があるため、奇数ビットを取り出すことができます。と偶数ビットをそれぞれ加算し、奇数ビットを左に 1 ビットシフトし、
偶数ビットを右に 1 ビットシフトして、加算の結果が交換後の結果になります。
コードデモ:
#include<stdio.h>
#define EXCHANGE(n) (((n&0x55555555)<<1)+((n&0xaaaaaaaa)>>1))
int main() {
int a = 21;
int b = EXCHANGE(a);
printf("%d", b);
return 0;
}
実行結果:
分析:
3. アレイを所定の位置から取り外します
演習内容:
配列内のすべての要素 val をその場で削除します。時間計算量は O(N)、空間計算量は O(1) です。 要件: 配列から削除する必要がある要素を削除した後、新しい配列を返します
。長さ。
問題解決のアイデア:
質問の意味に応じて、この質問にはダブル ポインタ メソッドを使用できます。最初に 1 つのポインタが配列の開始位置を指すようにし、次に 2 番目のポインタが for ループで移動します。削除する数値ではない数値が見つかると、その数値は削除されます。最初のポインターの位置に移動し、その後、最初のポインターを後方に移動して、最初のポインターが最終的に最後の配列の次の桁を指すようにします。 、その位置の添字は新しい配列の長さです。
コードデモ:
#include<stdio.h>
int removeElement(int* nums, int numsSize, int val) {
int pos = 0;
for (int i = 0; i < numsSize; i++) {
if (nums[i] != val) {
nums[pos] = nums[i];
pos++;
}
}
return pos;
}
int main() {
int arr[] = {
0,1,2,2,3,0,4,2 };
int val = 2;
int len = sizeof(arr) / sizeof(arr[0]);
int ret=removeElement(arr,len,val);
for (int i = 0; i < ret; i++) {
printf("%d ", arr[i]);
}
return 0;
}
実行結果:
分析:
要約する
これらの試験問題は代表的なものだと思いますので、ここで紹介させていただきますので、
皆さんも日々勉強して上達してください!