Created a stopwatch class

This commit is contained in:
2020-10-18 14:31:59 -04:00
parent 125bf9ddf7
commit c0ca08838d
3 changed files with 275 additions and 0 deletions

33
InvalidResult.ts Normal file
View File

@@ -0,0 +1,33 @@
//typescriptClasses/InvalidResult.ts
//Matthew Ellison
// Created: 10-18-20
//Modified: 10-18-20
//This file contains a class that is used to time the execution time of other programs
/*
Copyright (C) 2020 Matthew Ellison
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Lesser General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
export class InvalidResult{
private message: string;
public constructor(message: string){
this.message = message;
}
public getMessage(): string{
return this.message;
}
}

143
Stopwatch.ts Normal file
View File

@@ -0,0 +1,143 @@
//typescriptClasses/Stopwatch.ts
//Matthew Ellison
// Created: 10-18-20
//Modified: 10-18-20
//This file contains a class that is used to time the execution time of other programs
/*
Copyright (C) 2020 Matthew Ellison
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Lesser General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
import {InvalidResult} from "./InvalidResult";
import {performance} from "perf_hooks";
//An enum that helps keep track of how many times the time has been reduced in the getStr function
enum TIME_RESOLUTION{ NANOSECOND, MICROSECOND, MILLISECOND, SECOND, MINUTE, HOUR, ERROR };
export class Stopwatch{
private startTime: number;
private stopTime: number;
//Constructor makes sure all values are set to defaults
public constructor(){
//Make sure both values are null so it is easier to detect incorrect function calling order
this.startTime = null;
this.stopTime = null;
}
//Returns a long with the elapsed time in milliseconds. Used by other functions to get the time before converting it to the correct resolution
private getTime(): number{
if(this.startTime == null){
return 0;
}
else if(this.stopTime == null){
return performance.now() - this.startTime;
}
else{
return this.stopTime - this.startTime;
}
}
//Simultates starting a stopwatch by saving the time
public start(): void{
//Make sure the stop time is reset
this.stopTime = null;
//Get the time as close to returning from the function as possible
this.startTime = performance.now();
}
//Simulates stopping a stopwatch by saving the time
public stop(): void{
//Set the stopTime as close to call time as possible
this.stopTime = performance.now();
//If the startTime has not been set then reset stopTime
if(this.startTime == null){
this.stopTime = null;
}
}
//Resets all variables in the stopwatch
public reset(): void{
//Make sure all variables are reset correctly
this.startTime = null;
this.stopTime = null;
}
//Returns the time in nanoseconds
public getNano(): number{
return this.getTime() * 1000000;
}
//Returns the time in microseconds
public getMicro(): number{
return this.getTime() * 1000;
}
//Returns the time in milliseconds
public getMilli(): number{
return this.getTime();
}
//Returns the time in seconds
public getSecond(): number{
return this.getTime() / 1000;
}
//Returns the time in minutes
public getMinute(): number{
return this.getTime() / 60000;
}
//Returns the time in hours
public getHour(): number{
return this.getTime() / 3600000;
}
//Returns the time as a string at the 'best' resolution. (Goal is xxx.xxx)
public getStr(): string{
//Get the current duraction from time
return Stopwatch.getStr(this.getNano());
}
public static getStr(nanoseconds: number): string{
let duration: number = nanoseconds;
//Reduce the num,ber to the appropriate number of digits. (xxx.x).
//This loop works down to seconds
let resolution: TIME_RESOLUTION;
for(resolution = TIME_RESOLUTION.NANOSECOND;(resolution < TIME_RESOLUTION.SECOND) && (duration >= 1000);++resolution){
duration /= 1000;
}
//Check if the duration needs reduced to minutes
if((duration >= 120) && (resolution == TIME_RESOLUTION.SECOND)){
//Reduce to minutes
duration /= 60;
++resolution;
//Check if the duration needs reduced to hours
if(duration >= 60){
//Reduce to hours
duration /= 60;
++resolution;
}
}
//Turn the number into a string
let time: string = duration.toFixed(3);
//Tack on the appropriate suffix for resolution
switch(resolution){
case TIME_RESOLUTION.NANOSECOND: time += " nanoseconds"; break;
case TIME_RESOLUTION.MICROSECOND: time += " microseconds"; break;
case TIME_RESOLUTION.MILLISECOND: time += " milliseconds"; break;
case TIME_RESOLUTION.SECOND: time += " seconds"; break;
case TIME_RESOLUTION.MINUTE: time += " minutes"; break;
case TIME_RESOLUTION.HOUR: time += " hours"; break;
case TIME_RESOLUTION.ERROR:
default: throw new InvalidResult("timeResolution was invalid");
}
//Return the string
return time;
}
}

99
TestStopwatch.ts Normal file
View File

@@ -0,0 +1,99 @@
//typescriptClasses/TestStopwatch.ts
//Matthew Ellison
// Created: 10-18-20
//Modified: 10-18-20
//This file contains a class that is used to time the execution time of other programs
/*
Copyright (C) 2020 Matthew Ellison
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Lesser General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
import assert = require("assert");
import {Stopwatch} from "./Stopwatch";
let NUM_TO_RUN = 100000;
function testStartStop(): void{
let timer: Stopwatch = new Stopwatch();
timer.start();
timer.stop();
//If it gets to here without throwing an exception everything went well
console.log("start/stop passed");
}
function testConversion(): void{
let timer: Stopwatch = new Stopwatch();
let sum: number = 0;
//Start the timer
timer.start();
//Do something to run some time
for(let cnt: number = 0;cnt < NUM_TO_RUN;++cnt){
sum += cnt;
}
//Stop the timer
timer.stop();
//Assert something so the sum isn't ignored during compile
assert.notStrictEqual(sum, 0, "You really messed up");
//Check that the different resolutions work out correctly
let nano: number = timer.getNano();
assert.strictEqual(timer.getMicro(), nano / 1000, "Micro resolution test failed");
assert.strictEqual(timer.getMilli(), nano / 1000000, "Milli resolution test failed");
assert.strictEqual(timer.getSecond(), nano / 1000000000, "Minute resolution test failed");
assert.strictEqual(timer.getMinute(), nano / 60000000000, "Minute resolution test failed");
assert.strictEqual(timer.getHour(), nano / 3600000000000, "Hour resolution test failed");
console.log("conversion passed");
}
function testStringConversion(): void{
//Test nanoseconds
let results: string = Stopwatch.getStr(1.0);
assert.strictEqual(results, "1.000 nanoseconds", "String conversion to nanoseconds failed");
//Test microseconds
results = Stopwatch.getStr(1.0e3);
assert.strictEqual(results, "1.000 microseconds", "String conversion to microseconds failed");
//Test milliseconds
results = Stopwatch.getStr(1.0e6);
assert.strictEqual(results, "1.000 milliseconds", "String conversion to milliseconds failed");
//Test seconds
results = Stopwatch.getStr(1.0e9);
assert.strictEqual(results, "1.000 seconds", "String conversion to seconds failed");
//Test mintues
results = Stopwatch.getStr(1.0e12);
assert.strictEqual(results, "16.667 minutes", "String conversion to minutes failed");
//Rest hours
results = Stopwatch.getStr(1.0e13);
assert.strictEqual(results, "2.778 hours", "String conversion to hours failed");
console.log("string conversion passed");
}
//Run the functions
try{
testStartStop();
}
catch(error){
console.error("start/stop test failed!");
}
try{
testConversion();
}
catch(error){
console.error("conversion test failed!");
}
try{
testStringConversion();
}
catch(error){
console.error("string conversion test failed!");
}