Loading lang_c_12_perfs...
<assert.h>dont le rôle est de terminer brutalement le programme avec abort() (précédé d'un message explicite) si l'expression qui lui est transmise en paramètre est fausse.
<=à la place de
<sur la condition de la boucle par exemple).
... { int a=INT_MAX-5; int b=a+10; printf("%d + 10 = %d\n", a, b); ... }
-O3 -DNDEBUG -fomit-frame-pointer -ffast-math -march=nativeElles s'interprètent de la façon suivante :
#include <string.h> #include <ctype.h>
int // length of txt (as int) Perf_len(const char *txt) { return (int)strlen(txt); }
int // number of letters in txt Perf_alphaCount(const char *txt) { int count=0; for(int i=0; i<Perf_len(txt); ++i) // ugly! many calls to Perf_len() { if(isalpha(txt[i])) { ++count; } } return count; }
#include <sys/time.h>
double // seconds (1e-6 precision) since 1970/01/01 00:00:00 UTC now(void) { struct timeval tv; gettimeofday(&tv, NULL); return (double)tv.tv_sec+1e-6*(double)tv.tv_usec; }
#define TXT " This is a quite long text with many words. \n" \ " We aim at counting the number of letters it contains. \n" #define TXT_x30 TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT \ TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT
void test_alphaCount(void) { printf("\n~~~~ %s() ~~~~\n", __func__); const char *txt=TXT_x30; const double t0=now(); double duration=0.0; int iterCount; for(iterCount=0; duration<2.0; ++iterCount) { Perf_alphaCount(txt); duration=now()-t0; } printf("%g it/s\n", iterCount/duration); }
... { int *p=obtainAnAddress(); int a=(*p)*4; doSomething(); int b=(*p)+3; ... }
... { int *p=obtainAnAddress(); const int tmp=(*p); int a=tmp*4; doSomething(); int b=tmp+3; ... }
void Perf_mtxProduct(const double *aMtx, const double *bMtx, double *cMtx, index_t size) { for(index_t i=0; i<size; ++i) { for(index_t j=0; j<size; ++j) { const index_t cIdx=i*size+j; cMtx[cIdx]=0.0; for(index_t k=0; k<size; ++k) { const index_t aIdx=i*size+k, bIdx=k*size+j; cMtx[cIdx]+=aMtx[aIdx]*bMtx[bIdx]; // ugly! many stores to cMtx[cIdx] } } } }
typedef unsigned int index_t;
#define MTX_SIZE 100
void test_mtxProduct(void) { printf("\n~~~~ %s() ~~~~\n", __func__); double aMtx[MTX_SIZE*MTX_SIZE]; double bMtx[MTX_SIZE*MTX_SIZE]; double cMtx[MTX_SIZE*MTX_SIZE]; const double t0=now(); double duration=0.0; int iterCount; for(iterCount=0; duration<2.0; ++iterCount, duration=now()-t0) { Perf_mtxProduct(aMtx, bMtx, cMtx, MTX_SIZE); } printf("%g it/s\n", iterCount/duration); }
{ ... const index_t cIdx=i*size+j; #if 0 // first version cMtx[cIdx]=0.0; for(index_t k=0; k<size; ++k) { const index_t aIdx=i*size+k, bIdx=k*size+j; cMtx[cIdx]+=aMtx[aIdx]*bMtx[bIdx]; // ugly! many stores to cMtx[cIdx] } #else // second version double accum=0.0; for(index_t k=0; k<size; ++k) { const index_t aIdx=i*size+k, bIdx=k*size+j; accum+=aMtx[aIdx]*bMtx[bIdx]; } cMtx[cIdx]=accum; #endif ... }
//----------------------------------------------------------------------------
#ifndef PERF_H #define PERF_H
#define REPEAT_STRLEN 0
int // length of txt (as int) Perf_len(const char *txt);
int // number of letters in txt Perf_alphaCount(const char *txt);
#define USE_UNSIGNED_INDEX 0 #define USE_ACCUM 1
#if USE_UNSIGNED_INDEX typedef unsigned int index_t; #else typedef int index_t; #endif
void Perf_mtxProduct(const double *aMtx, const double *bMtx, double *cMtx, index_t size);
#endif // PERF_H
//----------------------------------------------------------------------------
//----------------------------------------------------------------------------
#include "perf.h" #include <string.h> #include <ctype.h>
int // length of txt (as int) Perf_len(const char *txt) { return (int)strlen(txt); }
int // number of letters in txt Perf_alphaCount(const char *txt) { int count=0; #if REPEAT_STRLEN for(int i=0; i<Perf_len(txt); ++i) // ugly! many calls to Perf_len() #else for(int i=0, len=Perf_len(txt); i<len; ++i) #endif { if(isalpha(txt[i])) { ++count; } } return count; }
void Perf_mtxProduct(const double *aMtx, const double *bMtx, double *cMtx, index_t size) { for(index_t i=0; i<size; ++i) { for(index_t j=0; j<size; ++j) { const index_t cIdx=i*size+j; #if USE_ACCUM double accum=0.0; for(index_t k=0; k<size; ++k) { const index_t aIdx=i*size+k, bIdx=k*size+j; accum+=aMtx[aIdx]*bMtx[bIdx]; } cMtx[cIdx]=accum; #else cMtx[cIdx]=0.0; for(index_t k=0; k<size; ++k) { const index_t aIdx=i*size+k, bIdx=k*size+j; cMtx[cIdx]+=aMtx[aIdx]*bMtx[bIdx]; // ugly! many stores to cMtx[cIdx] } #endif } } }
//----------------------------------------------------------------------------
//----------------------------------------------------------------------------
#include <stdio.h> #include <sys/time.h> #include "perf.h"
double // seconds (1e-6 precision) since 1970/01/01 00:00:00 UTC now(void) { struct timeval tv; gettimeofday(&tv, NULL); return (double)tv.tv_sec+1e-6*(double)tv.tv_usec; }
#define TXT " This is a quite long text with many words. \n" \ " We aim at counting the number of letters it contains. \n" #define TXT_x30 TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT \ TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT TXT
void test_alphaCount(void) { printf("\n~~~~ %s() ~~~~\n", __func__); printf("REPEAT_STRLEN=%d\n", REPEAT_STRLEN); const char *txt=TXT_x30; const double t0=now(); double duration=0.0; int iterCount; for(iterCount=0; duration<2.0; ++iterCount) { Perf_alphaCount(txt); duration=now()-t0; } printf("%g it/s\n", iterCount/duration); }
#define MTX_SIZE 100
void test_mtxProduct(void) { printf("\n~~~~ %s() ~~~~\n", __func__); printf("USE_UNSIGNED_INDEX=%d\n", USE_UNSIGNED_INDEX); printf("USE_ACCUM=%d\n", USE_ACCUM); double aMtx[MTX_SIZE*MTX_SIZE]; double bMtx[MTX_SIZE*MTX_SIZE]; double cMtx[MTX_SIZE*MTX_SIZE]; const double t0=now(); double duration=0.0; int iterCount; for(iterCount=0; duration<2.0; ++iterCount, duration=now()-t0) { Perf_mtxProduct(aMtx, bMtx, cMtx, MTX_SIZE); } printf("%g it/s\n", iterCount/duration); }
int main(void) { test_alphaCount(); test_mtxProduct(); return 0; }
//----------------------------------------------------------------------------