# Detecting a pattern in a time series with a Neural Network

I new to working with Neural Networks and I want to detect a pattern in a time series and return some measure of the certainty/uncertainty when a pattern has been detected:

data={1, 2.5, 1, 1.9, 0.10388, 0.7235, 0.8979, 0.97703, 0.151623, 0.319143, 1.2, \
2, 0.4068, 0.816, 0.470704, 0.072562, 0.313688, 0.7371, 0.19443, 1, \
2.1, 1.3, 1.5, 2, 0.243, 0.342, 0.8473, 0.18084, 0.63023, 0.889836, 0.3149, 0.8273, \
0.72881, 0.55363, 0.38214, 1, 2, 1, 0.672, 0.533, 0.69, 0.24837, 0.607, \
0.9488, 1, 2.7, 0.9, 2.2, 0.39696, 0.41164, 0.0979}


In this exemplary time series, the pattern I want to detect is 1,2,1,2. But the pattern in the time series is confounded by noise.

Working with Classify does not seem to work, since it only accepts at least two classes. So I'm having trouble finding the right function for this and hope for some help.

• Way too small data for "detecting a pattern" with a neural network. – Anton Antonov May 24 '18 at 21:07
• Yes of course! This is just an exemplary time series in order to clarify what I mean. The "real" data I want to apply it to has enough data points for training and testing. – holistic May 24 '18 at 22:04

## 1 Answer

Define pattern and level of noise:

pattern = {1, 2, 1, 2};
d = .01;


This makes a sample of time series with 50 points:

sample:=Flatten[Insert[
MeanFilter[RandomReal[2.5,46],1],
pattern + d RandomReal[{-1,1},4],
RandomInteger[{1,46}]]];


The pattern is randomly inserted in data smoothed out with MeanFilter. Your pattern is in orange frame:

ListStepPlot[sample, AspectRatio -> 1/7, ImageSize -> Full,
PlotTheme -> "Detailed", Filling -> Bottom]


## Method 1: no machine learning

If you need position of your pattern inside time series relaxing with respect given noise level, you do not need machine learning. Here is how to do it:

SequencePosition[sample,
{x_/;1-d<x<1+d,y_/;2-d<y<2+d,
z_/;1-d<z<1+d,w_/;2-d<w<2+d}]


{{21, 24}}

## Method 2: predicting position

To predict position of pattern inside the series you need Predict. First define a function that finds starting index of pattern exactly:

datapos[data_]:=SequencePosition[data,
{x_/;1-d<x<1+d,y_/;2-d<y<2+d,
z_/;1-d<z<1+d,w_/;2-d<w<2+d}][[1,1]]


Build training set of 10,000 samples:

trainingset = # -> datapos[#] & /@ Table[sample, 10000];


Train with quality:

p = Predict[trainingset, PerformanceGoal -> "Quality"]

PredictorInformation[p]


Compare exact and learned methods:

In[]:= {datapos[#],p[#]}&@(tmp=sample)
Out[]= {22,20.851}


See distribution:

Plot[Evaluate@PDF[p[tmp, "Distribution"], x], {x, 0, 50}, PlotRange -> All]


Build test set and measurements:

testset = # -> datapos[#] & /@ Table[sample, 100];
pm = PredictorMeasurements[p, testset]


Measure some stats:

In[]:= pm[ "StandardDeviation"]
Out[]= 1.50146

pm["ComparisonPlot"]


## Method 3: testing time series on presence of pattern

On the other hand if you have many time series samples which you need to test on the presence of the pattern (TRUE/FALSE) - you can use Classify, as you have 2 classes exactly. You can do the same steps below with a neural net too, but Classify will keep this simple.

Build a training set out of 10,000 samples the more the better:

trainingset = <|"TRUE" -> Table[sample, 5000],
"FALSE" -> Table[MeanFilter[RandomReal[2.5, 50], 1], 5000]|>;


Train with quality:

c = Classify[trainingset, PerformanceGoal -> "Quality"]


This is typical work of the classifier - pattern detected successfully with given probabilities:

In[]:= c[sample, "Probabilities"]
Out[]= <|"FALSE" -> 0.188043, "TRUE" -> 0.811957|>


Build test set:

testset = <|"TRUE" -> Table[sample, 100],
"FALSE" -> Table[MeanFilter[RandomReal[2.5, 50], 1], 100]|>;


Build measurements:

cm = ClassifierMeasurements[c, testset]


Good accuracy:

In[]:= cm["Accuracy"]
Out[]= 0.98


which can also be checked as:

cm["ConfusionMatrixPlot"]


My WL version:

In[]:= \$Version
Out[]= 11.3.0 for Mac OS X x86 (64-bit) (March 7, 2018)

• Thank you Vitaliy, this gives me a lot of information to get deeper into this topic, awesome :)! – holistic May 25 '18 at 9:06
• How do you find the location of the pattern using the third method? – Jerome Ibanes Feb 16 '19 at 21:00