copy old oref0 sensitivity code

This commit is contained in:
Milos Kozak 2017-06-24 15:04:22 +02:00
parent b39f59f59e
commit 70aaafa616
5 changed files with 266 additions and 109 deletions

View file

@ -215,6 +215,10 @@ public class ConfigBuilderPlugin implements PluginBase, PumpInterface, Constrain
return activePump;
}
public static SensitivityInterface getActiveSensitivity() {
return activeSensitivity;
}
void logPluginStatus() {
for (PluginBase p : pluginList) {
log.debug(p.getName() + ":" +

View file

@ -7,11 +7,11 @@ import java.util.Date;
*/
public class AutosensData {
long time = 0L;
public long time = 0L;
public String pastSensitivity = "";
public double deviation = 0d;
boolean nonCarbsDeviation = false;
boolean nonEqualDeviation = false;
public boolean nonEqualDeviation = false;
double absorbed = 0d;
public double carbsFromBolus = 0d;
public double cob = 0;

View file

@ -29,6 +29,7 @@ import info.nightscout.androidaps.events.EventNewBG;
import info.nightscout.androidaps.events.EventNewBasalProfile;
import info.nightscout.androidaps.events.EventPreferenceChange;
import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.plugins.ConfigBuilder.ConfigBuilderPlugin;
import info.nightscout.androidaps.plugins.IobCobCalculator.events.BasalData;
import info.nightscout.androidaps.plugins.IobCobCalculator.events.EventAutosensCalculationFinished;
import info.nightscout.androidaps.plugins.IobCobCalculator.events.EventNewHistoryData;
@ -55,9 +56,9 @@ public class IobCobCalculatorPlugin implements PluginBase {
private static Handler sHandler = null;
private static HandlerThread sHandlerThread = null;
private static Object dataLock = new Object();
private static final Object dataLock = new Object();
static IobCobCalculatorPlugin plugin = null;
private static IobCobCalculatorPlugin plugin = null;
public static IobCobCalculatorPlugin getPlugin() {
if (plugin == null)
@ -65,6 +66,14 @@ public class IobCobCalculatorPlugin implements PluginBase {
return plugin;
}
public static LongSparseArray<AutosensData> getAutosensDataTable() {
return autosensDataTable;
}
public static List<BgReading> getBucketedData() {
return bucketed_data;
}
@Override
public int getType() {
return GENERAL;
@ -120,7 +129,7 @@ public class IobCobCalculatorPlugin implements PluginBase {
}
public IobCobCalculatorPlugin() {
IobCobCalculatorPlugin() {
MainApp.bus().register(this);
if (sHandlerThread == null) {
sHandlerThread = new HandlerThread(IobCobCalculatorPlugin.class.getSimpleName());
@ -198,14 +207,14 @@ public class IobCobCalculatorPlugin implements PluginBase {
}
}
public void createBucketedData() {
private void createBucketedData() {
if (isAbout5minData())
createBucketedData5min();
else
createBucketedDataRecalculated();
}
public void createBucketedDataRecalculated() {
private void createBucketedDataRecalculated() {
synchronized (dataLock) {
if (bgReadings == null || bgReadings.size() < 3) {
bucketed_data = null;
@ -310,7 +319,7 @@ public class IobCobCalculatorPlugin implements PluginBase {
//log.debug("Releasing createBucketedData");
}
public void calculateSensitivityData() {
private void calculateSensitivityData() {
if (MainApp.getConfigBuilder() == null)
return; // app still initializing
//log.debug("Locking calculateSensitivityData");
@ -523,106 +532,10 @@ public class IobCobCalculatorPlugin implements PluginBase {
}
}
public static AutosensResult detectSensitivity(long fromTime, long toTime) {
String age = SP.getString(R.string.key_age, "");
int defaultHours = 24;
if (age.equals(MainApp.sResources.getString(R.string.key_adult))) defaultHours = 24;
if (age.equals(MainApp.sResources.getString(R.string.key_teenage))) defaultHours = 4;
if (age.equals(MainApp.sResources.getString(R.string.key_child))) defaultHours = 4;
int hoursForDetection = SP.getInt(R.string.key_openapsama_autosens_period, defaultHours);
long now = System.currentTimeMillis();
if (autosensDataTable == null || autosensDataTable.size() < 4) {
log.debug("No autosens data available");
return new AutosensResult();
}
AutosensData current = getAutosensData(toTime);
if (current == null) {
log.debug("No autosens data available");
return new AutosensResult();
}
List<Double> deviationsArray = new ArrayList<>();
String pastSensitivity = "";
int index = 0;
while (index < autosensDataTable.size()) {
AutosensData autosensData = autosensDataTable.valueAt(index);
if (autosensData.time < fromTime) {
index++;
continue;
}
if (autosensData.time > toTime) {
index++;
continue;
}
if (autosensData.time > now - hoursForDetection * 60 * 60 * 1000L)
deviationsArray.add(autosensData.nonEqualDeviation ? autosensData.deviation : 0d);
if (deviationsArray.size() > hoursForDetection * 60 / 5)
deviationsArray.remove(0);
pastSensitivity += autosensData.pastSensitivity;
int secondsFromMidnight = Profile.secondsFromMidnight(autosensData.time);
if (secondsFromMidnight % 3600 < 2.5 * 60 || secondsFromMidnight % 3600 > 57.5 * 60) {
pastSensitivity += "(" + Math.round(secondsFromMidnight / 3600d) + ")";
}
index++;
}
Double[] deviations = new Double[deviationsArray.size()];
deviations = deviationsArray.toArray(deviations);
Profile profile = MainApp.getConfigBuilder().getProfile();
double sens = profile.getIsf();
String ratioLimit = "";
String sensResult = "";
log.debug("Records: " + index + " " + pastSensitivity);
Arrays.sort(deviations);
double percentile = percentile(deviations, 0.50);
double basalOff = percentile * (60 / 5) / Profile.toMgdl(sens, profile.getUnits());
double ratio = 1 + (basalOff / profile.getMaxDailyBasal());
if (percentile < 0) { // sensitive
sensResult = "Excess insulin sensitivity detected";
} else if (percentile > 0) { // resistant
sensResult = "Excess insulin resistance detected";
} else {
sensResult = "Sensitivity normal";
}
log.debug(sensResult);
double rawRatio = ratio;
ratio = Math.max(ratio, SafeParse.stringToDouble(SP.getString("openapsama_autosens_min", "0.7")));
ratio = Math.min(ratio, SafeParse.stringToDouble(SP.getString("openapsama_autosens_max", "1.2")));
if (ratio != rawRatio) {
ratioLimit = "Ratio limited from " + rawRatio + " to " + ratio;
log.debug(ratioLimit);
}
log.error("Sensitivity to: " + new Date(toTime).toLocaleString() + " percentile: " + percentile);
AutosensResult output = new AutosensResult();
output.ratio = Round.roundTo(ratio, 0.01);
output.carbsAbsorbed = Round.roundTo(current.cob, 0.01);
output.pastSensitivity = pastSensitivity;
output.ratioLimit = ratioLimit;
output.sensResult = sensResult;
return output;
private static AutosensResult detectSensitivity(long fromTime, long toTime) {
return ConfigBuilderPlugin.getActiveSensitivity().detectSensitivity(fromTime, toTime);
}
public static JSONArray convertToJSONArray(IobTotal[] iobArray) {
JSONArray array = new JSONArray();
for (int i = 0; i < iobArray.length; i++) {

View file

@ -1,16 +1,34 @@
package info.nightscout.androidaps.plugins.SensitivityMK;
import android.support.v4.util.LongSparseArray;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.SensitivityInterface;
import info.nightscout.androidaps.plugins.IobCobCalculator.AutosensData;
import info.nightscout.androidaps.plugins.IobCobCalculator.AutosensResult;
import info.nightscout.androidaps.plugins.IobCobCalculator.IobCobCalculatorPlugin;
import info.nightscout.utils.Round;
import info.nightscout.utils.SP;
import info.nightscout.utils.SafeParse;
/**
* Created by mike on 24.06.2017.
*/
public class SensitivityMKPlugin implements PluginBase, SensitivityInterface{
private static Logger log = LoggerFactory.getLogger(SensitivityMKPlugin.class);
private static boolean fragmentEnabled = true;
private static boolean fragmentVisible = false;
@ -80,6 +98,103 @@ public class SensitivityMKPlugin implements PluginBase, SensitivityInterface{
@Override
public AutosensResult detectSensitivity(long fromTime, long toTime) {
return null;
LongSparseArray<AutosensData> autosensDataTable = IobCobCalculatorPlugin.getAutosensDataTable();
String age = SP.getString(R.string.key_age, "");
int defaultHours = 24;
if (age.equals(MainApp.sResources.getString(R.string.key_adult))) defaultHours = 24;
if (age.equals(MainApp.sResources.getString(R.string.key_teenage))) defaultHours = 4;
if (age.equals(MainApp.sResources.getString(R.string.key_child))) defaultHours = 4;
int hoursForDetection = SP.getInt(R.string.key_openapsama_autosens_period, defaultHours);
long now = System.currentTimeMillis();
if (autosensDataTable == null || autosensDataTable.size() < 4) {
log.debug("No autosens data available");
return new AutosensResult();
}
AutosensData current = IobCobCalculatorPlugin.getAutosensData(toTime);
if (current == null) {
log.debug("No autosens data available");
return new AutosensResult();
}
List<Double> deviationsArray = new ArrayList<>();
String pastSensitivity = "";
int index = 0;
while (index < autosensDataTable.size()) {
AutosensData autosensData = autosensDataTable.valueAt(index);
if (autosensData.time < fromTime) {
index++;
continue;
}
if (autosensData.time > toTime) {
index++;
continue;
}
if (autosensData.time > now - hoursForDetection * 60 * 60 * 1000L)
deviationsArray.add(autosensData.nonEqualDeviation ? autosensData.deviation : 0d);
if (deviationsArray.size() > hoursForDetection * 60 / 5)
deviationsArray.remove(0);
pastSensitivity += autosensData.pastSensitivity;
int secondsFromMidnight = Profile.secondsFromMidnight(autosensData.time);
if (secondsFromMidnight % 3600 < 2.5 * 60 || secondsFromMidnight % 3600 > 57.5 * 60) {
pastSensitivity += "(" + Math.round(secondsFromMidnight / 3600d) + ")";
}
index++;
}
Double[] deviations = new Double[deviationsArray.size()];
deviations = deviationsArray.toArray(deviations);
Profile profile = MainApp.getConfigBuilder().getProfile();
double sens = profile.getIsf();
String ratioLimit = "";
String sensResult = "";
log.debug("Records: " + index + " " + pastSensitivity);
Arrays.sort(deviations);
double percentile = IobCobCalculatorPlugin.percentile(deviations, 0.50);
double basalOff = percentile * (60 / 5) / Profile.toMgdl(sens, profile.getUnits());
double ratio = 1 + (basalOff / profile.getMaxDailyBasal());
if (percentile < 0) { // sensitive
sensResult = "Excess insulin sensitivity detected";
} else if (percentile > 0) { // resistant
sensResult = "Excess insulin resistance detected";
} else {
sensResult = "Sensitivity normal";
}
log.debug(sensResult);
double rawRatio = ratio;
ratio = Math.max(ratio, SafeParse.stringToDouble(SP.getString("openapsama_autosens_min", "0.7")));
ratio = Math.min(ratio, SafeParse.stringToDouble(SP.getString("openapsama_autosens_max", "1.2")));
if (ratio != rawRatio) {
ratioLimit = "Ratio limited from " + rawRatio + " to " + ratio;
log.debug(ratioLimit);
}
log.error("Sensitivity to: " + new Date(toTime).toLocaleString() + " percentile: " + percentile);
AutosensResult output = new AutosensResult();
output.ratio = Round.roundTo(ratio, 0.01);
output.carbsAbsorbed = Round.roundTo(current.cob, 0.01);
output.pastSensitivity = pastSensitivity;
output.ratioLimit = ratioLimit;
output.sensResult = sensResult;
return output;
}
}

View file

@ -1,16 +1,33 @@
package info.nightscout.androidaps.plugins.SensitivityOref0;
import android.support.v4.util.LongSparseArray;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import info.nightscout.androidaps.MainApp;
import info.nightscout.androidaps.R;
import info.nightscout.androidaps.data.Profile;
import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.SensitivityInterface;
import info.nightscout.androidaps.plugins.IobCobCalculator.AutosensData;
import info.nightscout.androidaps.plugins.IobCobCalculator.AutosensResult;
import info.nightscout.androidaps.plugins.IobCobCalculator.IobCobCalculatorPlugin;
import info.nightscout.utils.Round;
import info.nightscout.utils.SP;
import info.nightscout.utils.SafeParse;
/**
* Created by mike on 24.06.2017.
*/
public class SensitivityOref0Plugin implements PluginBase, SensitivityInterface{
public class SensitivityOref0Plugin implements PluginBase, SensitivityInterface {
private static Logger log = LoggerFactory.getLogger(IobCobCalculatorPlugin.class);
private static boolean fragmentEnabled = true;
private static boolean fragmentVisible = false;
@ -80,6 +97,114 @@ public class SensitivityOref0Plugin implements PluginBase, SensitivityInterface{
@Override
public AutosensResult detectSensitivity(long fromTime, long toTime) {
return null;
LongSparseArray<AutosensData> autosensDataTable = IobCobCalculatorPlugin.getAutosensDataTable();
String age = SP.getString(R.string.key_age, "");
int defaultHours = 24;
if (age.equals(MainApp.sResources.getString(R.string.key_adult))) defaultHours = 24;
if (age.equals(MainApp.sResources.getString(R.string.key_teenage))) defaultHours = 24;
if (age.equals(MainApp.sResources.getString(R.string.key_child))) defaultHours = 24;
int hoursForDetection = SP.getInt(R.string.key_openapsama_autosens_period, defaultHours);
long now = System.currentTimeMillis();
if (autosensDataTable == null || autosensDataTable.size() < 4) {
log.debug("No autosens data available");
return new AutosensResult();
}
AutosensData current = IobCobCalculatorPlugin.getLastAutosensData();
if (current == null) {
log.debug("No current autosens data available");
return new AutosensResult();
}
List<Double> deviationsArray = new ArrayList<>();
String pastSensitivity = "";
int index = 0;
while (index < autosensDataTable.size()) {
AutosensData autosensData = autosensDataTable.valueAt(index);
if (autosensData.time < fromTime) {
index++;
continue;
}
if (autosensData.time > toTime) {
index++;
continue;
}
if (autosensData.time > now - hoursForDetection * 60 * 60 * 1000L)
deviationsArray.add(autosensData.nonEqualDeviation ? autosensData.deviation : 0d);
if (deviationsArray.size() > hoursForDetection * 60 / 5)
deviationsArray.remove(0);
pastSensitivity += autosensData.pastSensitivity;
int secondsFromMidnight = Profile.secondsFromMidnight(autosensData.time);
if (secondsFromMidnight % 3600 < 2.5 * 60 || secondsFromMidnight % 3600 > 57.5 * 60) {
pastSensitivity += "(" + Math.round(secondsFromMidnight / 3600d) + ")";
}
index++;
}
Double[] deviations = new Double[deviationsArray.size()];
deviations = deviationsArray.toArray(deviations);
Profile profile = MainApp.getConfigBuilder().getProfile();
double sens = profile.getIsf();
double ratio = 1;
String ratioLimit = "";
String sensResult = "";
log.debug("Records: " + index + " " + pastSensitivity);
Arrays.sort(deviations);
for (double i = 0.9; i > 0.1; i = i - 0.02) {
if (IobCobCalculatorPlugin.percentile(deviations, (i + 0.02)) >= 0 && IobCobCalculatorPlugin.percentile(deviations, i) < 0) {
log.debug(Math.round(100 * i) + "% of non-meal deviations negative (target 45%-50%)");
}
}
double pSensitive = IobCobCalculatorPlugin.percentile(deviations, 0.50);
double pResistant = IobCobCalculatorPlugin.percentile(deviations, 0.45);
double basalOff = 0;
if (pSensitive < 0) { // sensitive
basalOff = pSensitive * (60 / 5) / Profile.toMgdl(sens, profile.getUnits());
sensResult = "Excess insulin sensitivity detected";
} else if (pResistant > 0) { // resistant
basalOff = pResistant * (60 / 5) / Profile.toMgdl(sens, profile.getUnits());
sensResult = "Excess insulin resistance detected";
} else {
sensResult = "Sensitivity normal";
}
log.debug(sensResult);
ratio = 1 + (basalOff / profile.getMaxDailyBasal());
double rawRatio = ratio;
ratio = Math.max(ratio, SafeParse.stringToDouble(SP.getString("openapsama_autosens_min", "0.7")));
ratio = Math.min(ratio, SafeParse.stringToDouble(SP.getString("openapsama_autosens_max", "1.2")));
if (ratio != rawRatio) {
ratioLimit = "Ratio limited from " + rawRatio + " to " + ratio;
log.debug(ratioLimit);
}
double newisf = Math.round(Profile.toMgdl(sens, profile.getUnits()) / ratio);
if (ratio != 1) {
log.debug("ISF adjusted from " + Profile.toMgdl(sens, profile.getUnits()) + " to " + newisf);
}
AutosensResult output = new AutosensResult();
output.ratio = Round.roundTo(ratio, 0.01);
output.carbsAbsorbed = Round.roundTo(current.cob, 0.01);
output.pastSensitivity = pastSensitivity;
output.ratioLimit = ratioLimit;
output.sensResult = sensResult;
return output;
}
}