5

I’m trying to create an application which predicts time to take a medicine depending on user lifestyle and medicine's restrictions.
I mean:

From a patient I take informations like:
• How many times and when does he/she eat his/her meals
• When does he/she wake up and go asleep
• How many pills does he/she have to take


From medicine's restrictions:
• Is a medicine should be eaten on empty stomach
• Is a medicine should be eaten with/without a meal
• Does a patient need to make a break inbetween meal and taking the medicine (it’s not showing on the screen below yet)
• etc

Sample dataset:
https://ibb.co/Gvry945

What type of model/mechanics/algorythm should I use to predict a time to take a medicine? Is regression the right one? I need to predict 1,2,3,4 sometimes 5 columns.

I wrote a simple code based on:
https://learn.microsoft.com/pl-pl/dotnet/machine-learning/tutorials/predict-prices
How to predict multiple labels with ML.NET using regression task?

It’s working fine and I can predict more than 1 column. But still, my problem is blank cells. When I’m trying to predict something from that data, it always shows a wrong value and it’s only working fine when all cells are complete.

So, should I spread out my dataset to few less datasets (where all cells are complete)? ex.:
https://ibb.co/m8HVPvb
When I only predict TimeToTakeMedicine1


https://ibb.co/qNk9xQL
When I predict TimeToTakeMedicine1 and TimeToTakeMedicine2


https://ibb.co/GnRc1c0
When I predict TimeToTakeMedicine1,TimeToTakeMedicine2, TimeToTakeMedicine3 and so on.

Is there any easier and better way to solve that?

Working code to predict TimeToTakeMedicine1,TimeToTakeMedicine2, TimeToTakeMedicine3 (for making it simple, I got rid of OnEmptyStomach,WithMeal and IsPossible)

using System;
using System.IO;
using Microsoft.ML;
using Microsoft.ML.Trainers;

namespace NextTry
{
    class Program
    {
        static readonly string _trainDataPath = Path.Combine(Environment.CurrentDirectory, "DataFolder", "DataForPredictT1T2T3.csv");


        static void Main(string[] args)
        {

            MLContext mlContext = new MLContext(seed: 0);
            var model = Train(mlContext, _trainDataPath);

            TestSinglePrediction(mlContext, model);


        }

        public static ITransformer Train(MLContext mlContext, string dataPath)
        {
            IDataView dataView = mlContext.Data.LoadFromTextFile<Medicine>(dataPath, hasHeader: true, separatorChar: ',');

            var pipelineForMeal1 = mlContext.Transforms.CopyColumns(outputColumnName: "Label", inputColumnName: "TimeToTakeMedicine1")      
                .Append(mlContext.Transforms.Concatenate("Features", "MealTime1", "MealTime2", "MealTime3", "MealCount", "ActivityHoursWakeUp",  "ActivityHoursSleep", "PillsCount"))
                .Append(mlContext.Regression.Trainers.FastTree())
                .Append(mlContext.Transforms.CopyColumns(outputColumnName: "timeToTakeMedicine1", inputColumnName: "Score"));


            var pipelineForMeal2 = mlContext.Transforms.CopyColumns(outputColumnName: "Label", inputColumnName: "TimeToTakeMedicine2")
                .Append(mlContext.Transforms.Concatenate("Features", "MealTime1", "MealTime2", "MealTime3", "MealCount", "ActivityHoursWakeUp", "ActivityHoursSleep", "PillsCount"))
                .Append(mlContext.Regression.Trainers.FastTree())
                .Append(mlContext.Transforms.CopyColumns(outputColumnName: "timeToTakeMedicine2", inputColumnName: "Score"));


            var pipelineForMeal3 = mlContext.Transforms.CopyColumns(outputColumnName: "Label", inputColumnName: "TimeToTakeMedicine3")
                .Append(mlContext.Transforms.Concatenate("Features", "MealTime1", "MealTime2", "MealTime3", "MealCount", "ActivityHoursWakeUp", "ActivityHoursSleep",  "PillsCount"))
                .Append(mlContext.Regression.Trainers.FastTree())
                .Append(mlContext.Transforms.CopyColumns(outputColumnName: "timeToTakeMedicine3", inputColumnName: "Score"));


            var model = pipelineForMeal1
                .Append(pipelineForMeal2)
                .Append(pipelineForMeal3)
                .Fit(dataView);
            return model;
        }


        private static void TestSinglePrediction(MLContext mlContext, ITransformer model)
        {
            var predictionFunction = mlContext.Model.CreatePredictionEngine<Medicine, MedicineTimeTakeMedicinePrediction>(model);
            var medicineSample = new Medicine()
            {
                MealTime1 = 6,
                MealTime2 = 12,
                MealTime3 = 22,     
                MealCount = 3,
                PillsCount = 3
            };
            var prediction = predictionFunction.Predict(medicineSample);


            Console.WriteLine($"Predicted TimeToTakePill: {prediction.TimeToTakeMedicine1:0.####} ");
            Console.WriteLine($"Predicted TimeToTakePill: {prediction.TimeToTakeMedicine2:0.####}");
            Console.WriteLine($"Predicted TimeToTakePill: {prediction.TimeToTakeMedicine3:0.####}");


            Console.ReadKey();
        }
    }
}

using System;
using System.Collections.Generic;
using System.Text;
using Microsoft.ML.Data;

namespace NextTry
{
    public class Medicine

    {
        [LoadColumn(0)]
        public float MealTime1 { get; set; }

        [LoadColumn(1)]
        public float MealTime2 { get; set; }

        [LoadColumn(2)]
        public float MealTime3 { get; set; }

        [LoadColumn(3)]
        public float MealCount { get; set; }

        [LoadColumn(4)]
        public float ActivityHoursWakeUp { get; set; }

        [LoadColumn(5)]
        public float ActivityHoursSleep { get; set; }

        [LoadColumn(6)]
        public float PillsCount { get; set; }

        [LoadColumn(7)]
        public float TimeToTakeMedicine1 { get; set; }

        [LoadColumn(8)]
        public float TimeToTakeMedicine2 { get; set; }

        [LoadColumn(9)]
        public float TimeToTakeMedicine3 { get; set; }




    }
    public class MedicineTimeTakeMedicinePrediction

    {
        [ColumnName("timeToTakeMedicine1")]
        public float TimeToTakeMedicine1 { get; set; }

        [ColumnName("timeToTakeMedicine2")]
        public float TimeToTakeMedicine2 { get; set; }

        [ColumnName("timeToTakeMedicine3")]
        public float TimeToTakeMedicine3 { get; set; }


    }
}
Andreas Rossberg
  • 34,518
  • 3
  • 61
  • 72
Killua94
  • 51
  • 1
  • 2

1 Answers1

-1

I am running into the same issue. One thing that you do is to immediately append all the models into one pipeline as you have the same features.

MosGeo
  • 1,012
  • 9
  • 9