1 package com.android.bluetooth.tests; 2 3 import java.util.ArrayList; 4 5 /** 6 * Class for collecting test results, and presenting them in different formats. 7 * @author cbonde 8 * 9 */ 10 public class TestResultLogger implements IResultLogger { 11 12 private ArrayList<Result> mResults; 13 14 private class Result { 15 public long timeStamp; // ms precision Unix Time UTC. 16 public long receivedBytes; Result(long t, long b)17 public Result(long t, long b) { 18 timeStamp = t; 19 receivedBytes = b; 20 } 21 } 22 TestResultLogger()23 private TestResultLogger() { 24 mResults = new ArrayList<Result>(1000); 25 } 26 createLogger()27 public static IResultLogger createLogger(){ 28 return new TestResultLogger(); 29 } 30 31 @Override addResult(long bytesTransfered)32 public void addResult(long bytesTransfered) { 33 mResults.add(new Result(System.currentTimeMillis(), bytesTransfered)); 34 } 35 36 @Override getAverageSpeed()37 public int getAverageSpeed() { 38 if(mResults.size() < 1){ 39 return 0; 40 } 41 Result first = mResults.get(0); 42 Result last = mResults.get(mResults.size()-1); 43 // Multiply by 1000 to convert from ms to sec without loss 44 // of precision. 45 return (int) ((1000*(last.receivedBytes + first.receivedBytes))/ 46 (last.timeStamp - first.timeStamp+1)); 47 } 48 49 /** 50 * Optimized to perform best when period is closest to the last 51 * result entry. 52 * If the period does not match a log entry, an estimate will be made 53 * to compensate. 54 * If the result log does not contain data to cover the entire period 55 * the resulting value will represent the average speed of the content 56 * in the log. 57 */ 58 @Override getAverageSpeed(long period)59 public int getAverageSpeed(long period) { 60 Result preFirst = null; 61 Result first = mResults.get(0); 62 int i = mResults.size()-1; 63 Result last = mResults.get(i--); 64 long firstTimeStamp = last.timeStamp - period; 65 if(first.timeStamp > firstTimeStamp || mResults.size() < 3) { 66 // Not enough data, use total average 67 return getAverageSpeed(); 68 } 69 for(; i >= 0 ; i--) { 70 preFirst = mResults.get(i); 71 if(preFirst.timeStamp < firstTimeStamp) { 72 first = mResults.get(i+1); 73 break; 74 } 75 } 76 long timeError = period - (last.timeStamp-first.timeStamp); 77 long errorBytes = 0; 78 if(timeError > 0) { 79 // Find the amount of bytes to use for correction 80 errorBytes = (timeError*(preFirst.receivedBytes - first.receivedBytes)) 81 /(preFirst.timeStamp - first.timeStamp+1); 82 } 83 // Calculate the result 84 return (int) ((1000*(errorBytes+last.receivedBytes-first.receivedBytes))/period); 85 } 86 87 88 } 89