Tiens, dis-moi, j'essaye le même genre de truc sur la version indices, qui maintient une liste les indices des colonnes pertinentes :
intmatrix_elements_sum_indices_branchless(conststd::vector<std::vector<int>>&matrix){constintrow_size(matrix[0].size());std::vector<int>usable_columns(row_size);constautousable_columns_begin(usable_columns.begin());autousable_columns_end(usable_columns.end());std::iota(usable_columns_begin,usable_columns_end,0);intremaining_count(row_size);intresult(0);for(conststd::vector<int>&row:matrix)for(autoit(usable_columns_begin);it!=usable_columns_end;){constinti(*it);constintv(row[i]);result+=v;constintkeep_mask((v==0)?0:-1);usable_columns_end+=~keep_mask;// discussion ci-dessous sur le code d'ici...constintdistance_to_last(usable_columns_end-it);constautonew_i_it(it+(distance_to_last&~keep_mask));*it=*new_i_it;// ...à là.it+=-keep_mask;}returnresult;}
Ça ne fonctionne pas très bien et je pense que c'est à cause de l'écriture dans le bloc d'ici à là. Si je mets à la place de ce bloc la condition suivante :
if(~keep_mask)*it=*usable_columns_end;
Alors ça fonctionne très bien.
Ma compréhension est grosso-modo que dans la première version on réécrit inconditionnellement dans la mémoire pointée par it, et bien qu'elle est probablement en cache (on vient juste d'y accéder) et que sa valeur ne change pas toujours, la ligne de cache devient toujours dirty et il faut la renvoyer en RAM. Du coup on paye une écriture à chaque itération, qui coûte bien plus cher qu'une misprediction occasionnelle. Qu'en penses tu ?
[^] # Re: Quitte à faire du branchless
Posté par Julien Jorge (site web personnel) . En réponse au journal Exercices de programmation et benchmarks. Évalué à 2.
Tiens, dis-moi, j'essaye le même genre de truc sur la version
indices, qui maintient une liste les indices des colonnes pertinentes :Ça ne fonctionne pas très bien et je pense que c'est à cause de l'écriture dans le bloc d'ici à là. Si je mets à la place de ce bloc la condition suivante :
Alors ça fonctionne très bien.
Ma compréhension est grosso-modo que dans la première version on réécrit inconditionnellement dans la mémoire pointée par
it, et bien qu'elle est probablement en cache (on vient juste d'y accéder) et que sa valeur ne change pas toujours, la ligne de cache devient toujours dirty et il faut la renvoyer en RAM. Du coup on paye une écriture à chaque itération, qui coûte bien plus cher qu'une misprediction occasionnelle. Qu'en penses tu ?