问题描述
我使用最小可重现示例 (MRE) 复制了 Igor Ostrovsky 的博客“Gallery of Processor Cache Effects”中提到的示例 2,以测量每个 K 的运行时间.博客中的K与以下MRE中的变量STEP
相同:
import java.io.FileWriter;
import java.io.IOException;
import java.util.Map;
import java.util.TreeMap;
public class DemonstrateCachingAndDataPrefetching {
public static void main(String[] args) throws IOException {
//Fetching environment from command line arguments.
String environment = args[0];
//Integer array of predefined size (chosen randomly) and acts as the prime data for the experiment.
int[] arr = new int[64 * 1024 * 1024];
//Domain for the values of STEP
int[] STEP_DOMAIN = new int[]{1,2,4,8,16,32,64,128,256,512,1024,2048,4096,8096};
//Map to store the cumulative runtime for each value of STEP.
TreeMap<Integer,Long> map = new TreeMap<Integer,Long>();
//Number of times the runtime is computed for each value of STEP and then is averaged out.
int RUNS = 1000;
for (int STEP : STEP_DOMAIN){
//Initializing the cumulative time for each value of STEP to 0.
map.put(STEP,(long)0);
for(int run = 0; run < RUNS; run++){
long startTime = System.nanoTime();
//Generalized Task
for (int i = 0; i < arr.length; i += STEP){
arr[i] *= 3;
}
long estimatedTime = System.nanoTime() - startTime;
long cumulativeTimeForStep = map.get(STEP);
cumulativeTimeForStep += estimatedTime;
map.put(STEP,cumulativeTimeForStep);
}
}
FileWriter myWriter = new FileWriter(String.format("results-%1$s.csv",environment));
myWriter.write("STEP,RUNTIME\n");
for(Map.Entry m:map.entrySet()){
Double averageValue = Double.parseDouble(m.getValue()+"");
averageValue /= (double)RUNS;
myWriter.write(m.getKey() + "," + String.format("%.02f",averageValue) + "\n");
}
myWriter.close();
}
}
我使用 sysctl 检查了 Apple M1 cpu 的缓存线大小。它返回128 Bytes,如下图所示:
问题:
由于缓存行大小为 128 字节,JAVA 中的整数大小为 4 字节,因此对于变量 STEP
= {4,32} 的值,运行时应该几乎相同,并且64 如果支持数据读取。
但是,STEP
= 32 的运行时间值明显大于变量 STEP
= {8,64} 的运行时间值,如图所示如下图:
如果是 Intel cpu,变量 STEP
= {8,64} 的值的运行时间将几乎相同(因为缓存行大小是128 字节)。 但是,Apple M1 cpu 并非如此。
对这种不一致的任何暗示表示赞赏。
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)