クラスメートの何人かが、過去数日間、StackOverflow で同じ課題について実際に質問しようとしていることに気付きました。そのため、削除された 1 つの質問のコンテキスト (ただし、まだキャッシュされている) を恥知らずにコピー ペースト (のみ) します。 Google で回答なし) を使用して時間を節約できます。あらかじめお詫び申し上げます。
コンテキスト
システムの L2 キャッシュのデータ スループット (MB/秒) を測定する C プログラムを作成しようとしています。測定を実行するには、配列 A を配列 B にコピーし、複数回繰り返し、スループットを測定するプログラムを作成する必要があります。
少なくとも 2 つのシナリオを検討してください。
- 両方のフィールドが L2 キャッシュに収まります
- 配列のサイズは、L2 キャッシュのサイズよりも大幅に大きくなっています。
string.h から memcpy() を使用して配列をコピーし、両方の配列をいくつかの値 (たとえば、rand() を使用した乱数) で初期化し、少なくとも 100 回繰り返します。そうしないと、違いがわかりません。
配列のサイズと繰り返しの数は、入力パラメーターである必要があります。配列サイズの 1 つは、L2 キャッシュ サイズの半分にする必要があります。
質問
課題のコンテキストに基づいて、私が何をする必要があるかについて良い考えを持っています。問題は、作業用のテンプレート コードが提供されたのですが、その一部を解読するのに苦労していることです。誰かが何が起こっているのかを理解するのを手伝ってくれたら本当にありがたい.
コードは次のとおりです。
/* do not add other includes */
#include <stdio.h>
#include <stdlib.h>
#include <sys/time.h>
#include <time.h>
#include <string.h>
double getTime(){
struct timeval t;
double sec, msec;
while (gettimeofday(&t, NULL) != 0);
sec = t.tv_sec;
msec = t.tv_usec;
sec = sec + msec/1000000.0;
return sec;
}
/* for task 1 only */
void usage(void)
{
fprintf(stderr, "bandwith [--no_iterations iterations] [--array_size size]\n");
exit(1);
}
int main (int argc, char *argv[])
{
double t1, t2;
/* variables for task 1 */
unsigned int size = 1024;
unsigned int N = 100;
unsigned int i;
/* declare variables; examples, adjust for task */
int *A;
int *B;
/* parameter parsing task 1 */
for(i=1; i<(unsigned)argc; i++) {
if (strcmp(argv[i], "--no_iterations") == 0) {
i++;
if (i < argc)
sscanf(argv[i], "%u", &N);
else
usage();
} else if (strcmp(argv[i], "--array_size") == 0) {
i++;
if (i < argc)
sscanf(argv[i], "%u", &size);
else
usage();
} else usage();
}
/* allocate memory for arrays; examples, adjust for task */
A = malloc (size*size * sizeof (int));
B = malloc (size*size * sizeof (int));
/* initialise arrray elements */
t1 = getTime();
/* code to be measured goes here */
t2 = getTime();
/* output; examples, adjust for task */
printf("time: %6.2f secs\n",t2 - t1);
/* free memory; examples, adjust for task */
free(B);
free(A);
return 0;
}
私の質問は次のとおりです。
- 使用方法の目的は何ですか?
- 私が知る限り、それは常に使用法()につながり、sscanf行でパラメーターを取りません。
- この割り当てでは、配列のサイズを KB または MB で記録することを意図しています。malloc はサイズをバイト単位で割り当て、
size
変数値が 1024 の場合は 1MB * sizeof(int) になることがわかっています (少なくとも)。この場合、記録する必要がある配列サイズは 1MB または 1MB * sizeof(int) でしょうか? - パラメータの受け渡しが適切に機能し、パラメータを渡して
size
変数の値を変更した場合、配列のサイズは常にsize
変数の 2 乗になりますか?size
それとも、配列のサイズは単なる変数と見なされますか? これらすべてについて何かが欠けていない限り、サイズだけでなくサイズ*サイズをmallocするのは非常に直感的ではないようです。 - スループットの測定についての私の理解では、配列サイズに反復回数を掛けてから、かかった時間で割ります。これが正しいという確証を得ることはできますか?
これらは、この課題を理解する上での唯一のハードルです。どんな助けでも大歓迎です。