From 4493fbb0fac880b9e43a11488bb27fe756489a50 Mon Sep 17 00:00:00 2001 From: Starbeamrainbowlabs Date: Tue, 30 Jul 2019 15:42:37 +0100 Subject: [PATCH] Tidy up normalising code --- common/Normalisers.mjs | 69 ++++++++++++++++++++++ server/settings.default.toml | 5 -- server/train-ai/DatasetFetcher.mjs | 94 ++++++++---------------------- 3 files changed, 92 insertions(+), 76 deletions(-) create mode 100644 common/Normalisers.mjs diff --git a/common/Normalisers.mjs b/common/Normalisers.mjs new file mode 100644 index 0000000..53f87b9 --- /dev/null +++ b/common/Normalisers.mjs @@ -0,0 +1,69 @@ +import { normalise, clamp } from './Math.mjs'; + +function normalise_lat(lat) { + return normalise(lat, + { min: -90, max: +90 }, + { min: 0, max: 1 } + ); +} + +function normalise_lng(lng) { + return normalise(lng, + { min: -180, max: +180 }, + { min: 0, max: 1 } + ); +} + +function unnormalise_lat(nlat) { + return normalise(nlat, + { min: 0, max: 1 }, + { min: -90, max: +90 } + ); +} + +function unnormalise_lng(nlng) { + return normalise(nlng, + { min: 0, max: 1 }, + { min: -180, max: +180 } + ); +} + +function normalise_gateway_distance(distance) { + return clamp(normalise(distance, + { min: 0, max: 20000 }, + { min: 0, max: 1 } + ), 0, 20000); +} + +function unnormalise_gateway_distance(ndistance) { + return clamp(normalise(ndistance, + { min: 0, max: 1 }, + { min: 0, max: 20000 } + ), 0, 20000); +} + +function normalise_rssi(rssi) { + return clamp(normalise(rssi, + { min: -150, max: 0 }, + { min: 0, max: 1 } + ), 0, 1) +} +function unnormalise_rssi(rssi) { + return clamp(normalise(rssi, + { min: 0, max: 1 }, + { min: -150, max: 0 } + ), 0, 1) +} + +export { + normalise_lat, + normalise_lng, + unnormalise_lat, + unnormalise_lng, + + normalise_gateway_distance, + unnormalise_gateway_distance, + + normalise_rssi, + unnormalise_rssi +}; diff --git a/server/settings.default.toml b/server/settings.default.toml index db68936..0dd67dc 100644 --- a/server/settings.default.toml +++ b/server/settings.default.toml @@ -54,11 +54,6 @@ devices = [ [ai] # Settings relating to the training of the AI. Note that a number of these settings can also be specified by environment variables, to aid with fiddling with the parameters to find the right settings. -# Min / max dataset values when training the AI, since neural networks only take values between 0 and 1. -# Note that changing these means that you've got to retrain the AIs all over again! -rssi_min = -150 -rssi_max = 0 - # The architecture of the neural network, as an arary of integers. # Each integer represents the number of nodes in a layer of the neural network. network_arch = [ 64 ] diff --git a/server/train-ai/DatasetFetcher.mjs b/server/train-ai/DatasetFetcher.mjs index e3b4756..4bd5919 100644 --- a/server/train-ai/DatasetFetcher.mjs +++ b/server/train-ai/DatasetFetcher.mjs @@ -2,7 +2,12 @@ import haversine from 'haversine-distance'; -import { normalise, clamp } from '../../common/Math.mjs'; +import { + normalise_lat, + normalise_lng, + normalise_rssi, + normalise_gateway_distance, +} from '../../common/Normalisers.mjs'; class DatasetFetcher { constructor({ settings, GatewayRepo, RSSIRepo, ReadingRepo }) { @@ -12,92 +17,39 @@ class DatasetFetcher { this.repo_reading = ReadingRepo; } - normalise_latlng(lat, lng) { - return { - latitude: normalise(lat, - { min: -90, max: +90 }, - { min: 0, max: 1 } - ), - longitude: normalise(lng, - { min: -180, max: +180 }, - { min: 0, max: 1 } - ) - }; - } - fetch_all(gateway_id) { let gateway_location = this.repo_gateway.get_by_id(gateway_id); let result = []; for(let rssi of this.repo_rssi.iterate_gateway(gateway_id)) { - let next_input = this.normalise_latlng(rssi.latitude, rssi.longitude); - let distance_from_gateway = haversine(gateway_location, rssi); - - next_input.distance = clamp( - normalise(distance_from_gateway, - { min: 0, max: 20000 }, - { min: 0, max: 1 } - ), - 0, 1); - - // console.log(`Distance from gateway: ${haversine(gateway_location, rssi)}m`); - - let next_output = [ - clamp(normalise(rssi.rssi, - { min: this.settings.ai.rssi_min, max: this.settings.ai.rssi_max }, - { min: 0, max: 1 } - ), 0, 1) - ]; - result.push({ - input: next_input, - output: next_output + input: { + latitude: normalise_lat(rssi.latitude), + longitude: normalise_lng(rssi.longitude), + distance: normalise_gateway_distance( + haversine(gateway_location, rssi) + ) + }, + output: [ + normalise_rssi(rssi.rssi) + ] }); } for(let reading of this.repo_reading.iterate_unreceived()) { - let next_input = this.normalise_latlng( - reading.latitude, - reading.longitude - ); - next_input.distance = clamp( - normalise(haversine(gateway_location, reading), - { min: 0, max: 20000 }, - { min: 0, max: 1 } - ), - 0, 1); - result.push({ - input: next_input, + input: { + latitude: normalise_lat(reading.latitude), + longitude: normalise_lng(reading.longitude), + distance: normalise_gateway_distance( + haversine(gateway_location, reading) + ) + }, output: [ 0 ] }); } - return result; } - - *fetch_input(gateway_id) { - for(let rssi of this.repo_rssi.iterate_gateway(gateway_id)) - yield this.normalise_latlng(rssi.latitude, rssi.longitude); - - for(let rssi of this.repo_reading.iterate_unreceived()) - yield this.normalise_latlng(rssi.latitude, rssi.longitude); - } - - *fetch_output(gateway_id) { - for(let rssi of this.repo_rssi.iterate_gateway(gateway_id)) { - yield [ - clamp(normalise(rssi.rssi, - { min: this.settings.ai.rssi_min, max: this.settings.ai.rssi_max }, - { min: 0, max: 1 } - ), 0, 1) - ]; - } - // Yield 0 for every unreceived message, since we want to train it to predict a *terrible* signal where the gateway is not - for(let rssi of this.repo_reading.iterate_unreceived()) { - yield [ 0 ]; - } - } } export default DatasetFetcher;