2017-07-25 1 views
12

Tenir compte de ce tableau imbriqué des dates et des noms:: Découvrez la séquence dates

var fDates = [ 
    ['2015-02-03', 'name1'], 
    ['2015-02-04', 'nameg'], 
    ['2015-02-04', 'name5'], 
    ['2015-02-05', 'nameh'], 
    ['1929-03-12', 'name4'], 
    ['2023-07-01', 'name7'], 
    ['2015-02-07', 'name0'], 
    ['2015-02-08', 'nameh'], 
    ['2015-02-15', 'namex'], 
    ['2015-02-09', 'namew'], 
    ['1980-12-23', 'name2'], 
    ['2015-02-12', 'namen'], 
    ['2015-02-13', 'named'], 
] 

Comment puis-je identifier les dates qui sont hors de séquence. Je me fiche de savoir si les dates se répètent, ou si je saute, j'ai juste besoin de celles qui ne sont pas en ordre. -À-dire, je reviens:

results = [ 
    ['1929-03-12', 'name4'], 
    ['2023-07-01', 'name7'], 
    ['2015-02-15', 'namex'], 
    ['1980-12-23', 'name2'], 
] 

(« Namex » est moins évident, mais ce n'est pas dans l'ordre général de la liste.)

Cela semble être une variation sur la plus longue augmentation Subsequence (LIS), avec la mise en garde qu'il pourrait y avoir des dates répétées dans la séquence, mais ne devrait jamais revenir en arrière. Cas d'utilisation: J'ai trié et daté des enregistrements et j'ai besoin de trouver ceux dont les dates sont "suspectes" - peut-être une erreur de saisie - à signaler pour vérification.


NB1: J'utilise Javascript droit et pas un cadre. (Je suis dans le noeud, mais je cherche une solution sans paquetage donc je peux comprendre ce qui se passe ...)

+0

Les tentatives méritent d'être partagées _toujours_.Vous pourriez être sur le bon chemin, ou sur un chemin totalement faux, mais votre tentative sera instructive et aidera à informer la façon dont nous présentons une réponse. Ne sois pas timide! :) – msanford

+6

Quelle est la situation réelle ici qui vous oblige à le faire? – Ryan

+0

@Ryan Bon point. Dans mon cas d'utilisation, il est hautement improbable (proche de 0) qu'il y ait deux sous-séquences de longueurs égales. – Trees4theForest

Répondre

5

est ici une adaptation de Rosetta Code LIS à prendre les fonctions personnalisées getElement et compare. Nous pouvons affiner les fonctions de comparaison et d'obtention d'éléments en fonction de vos besoins spécifiques.

function f(arr, getElement, compare){ 
 
    function findIndex(input){ 
 
    var len = input.length; 
 
    var maxSeqEndingHere = new Array(len).fill(1) 
 
    for(var i=0; i<len; i++) 
 
     for(var j=i-1;j>=0;j--) 
 
     if(compare(getElement(input, i), getElement(input, j)) && maxSeqEndingHere[j] >= maxSeqEndingHere[i]) 
 
      maxSeqEndingHere[i] = maxSeqEndingHere[j]+1; 
 
    return maxSeqEndingHere; 
 
    } 
 

 
    function findSequence(input, result){ 
 
    var maxValue = Math.max.apply(null, result); 
 
    var maxIndex = result.indexOf(Math.max.apply(Math, result)); 
 
    var output = new Set(); 
 
    output.add(maxIndex); 
 
    for(var i = maxIndex ; i >= 0; i--){ 
 
     if(maxValue==0)break; 
 
     if(compare(getElement(input, maxIndex), getElement(input, i)) && result[i] == maxValue-1){ 
 
     output.add(i); 
 
     maxValue--; 
 
     } 
 
    } 
 

 
    return output; 
 
    } 
 

 
    var result = findIndex(arr); 
 
    var final = findSequence(arr, result) 
 
    return arr.filter((e, i) => !final.has(i)); 
 
} 
 

 
var fDates = [ 
 
    ['2015-02-03', 'name1'], 
 
    ['2015-02-04', 'nameg'], 
 
    ['2015-02-04', 'name5'], 
 
    ['2015-02-05', 'nameh'], 
 
    ['1929-03-12', 'name4'], 
 
    ['2023-07-01', 'name7'], 
 
    ['2015-02-07', 'name0'], 
 
    ['2015-02-08', 'nameh'], 
 
    ['2015-02-15', 'namex'], 
 
    ['2015-02-09', 'namew'], 
 
    ['1980-12-23', 'name2'], 
 
    ['2015-02-12', 'namen'], 
 
    ['2015-02-13', 'named'], 
 
]; 
 

 
console.log(f(fDates, (arr, i) => arr[i][0], (a,b) => a >= b));

+0

Pouvez-vous m'aider à comprendre pourquoi vous passez '(a, b) => a> = b;' dans l'argument de comparaison? – Trees4theForest

+0

@ Trees4theForest comme je l'ai compris à partir de vos dates de question peut répéter, d'où les "égaux". La fonction est passée au code LIS, qui a été écrit à l'origine avec '>'. –

+0

Ahh. Merci. Donc '(a, b) => a> b' exclurait les éléments répétés ... slick. – Trees4theForest

1

Utilisez le Javascript Date type. Comparez avec ces objets. Très simpliste,

date1 = new Date(fDates[i, 0]) 
date2 = new Date(fDates[i+1, 0]) 
if (date2 < date1) { // or whatever comparison you want ... 
    // flag/print/alert the date 
} 

Pour clarifier les choses, ce trouve simplement des éléments hors séquence. Vous pouvez le faire avec des chaînes, comme Jaromanda X a souligné. Cependant, vous utilisez l'expression "way out of line"; Peu importe ce que cela signifie pour vous, Date devrait vous permettre de le déterminer et de le tester. Par exemple, est-ce que '2023-07-01' est inacceptable parce que c'est dans 8 ans, ou simplement parce qu'il est hors service avec les dates de 2015? Vous voudrez peut-être une comparaison à un laps de temps plus simple, comme un mois où votre comparaison sera ressemble à quelque chose comme

if (date2-date1 > one_month) 
+2

pas besoin de Date - le tri par chaîne fonctionnera pour AAAA-MM-JJ: p –

+0

La chaîne va trier, mais elle ne donne pas autant de facilité pour "sortir de la ligne". Je ne suis pas en train de définir cela pour OP. – Prune

+0

Je comprends parfaitement: p –

2

Examiner toutes les erreurs d'entrée possibles, je pris la liberté de extension les fDates tableau. Si l'algoritmo est juste, il devrait attraper toutes les probabilités probables suivantes.

var fDates = [ 
 
    ['2015-02-03', 'name1'], 
 
    ['2015-02-04', 'nameg'], 
 
    ['2015-02-04', 'name5::Repeating Date(Accepted)'], 
 
    ['2015-02-06', 'name5::Skipped a Date(Accepted)'], 
 
    ['1929-03-12', 'name4::An Old Date'], 
 
    ['2023-07-01', 'name7::Too Far future date'], 
 
    ['2015-02-07', 'name0'], 
 
    ['2015-02-08', 'nameh'], 
 
    ['2015-02-15', 'nameh::Wrong future date, Type1'], 
 
    ['2015-02-08', 'namew'], 
 
    ['2015-02-17', 'nameh::Wrong future date, Type2'], 
 
    ['2015-02-09', 'namew'], 
 
    ['2015-02-17', 'nameh::Wrong future date, Type3'], 
 
    ['2015-02-11', 'namew'], 
 
    ['2015-02-17', 'nameh::Wrong future multiple, #1'], 
 
    ['2015-02-19', 'nameh::Wrong future multiple, #2'], 
 
    ['2015-02-12', 'namew'], 
 
] 
 
var results = filterDates(fDates); 
 
console.log(JSON.stringify(results).replace(/],/g,"],\n")); 
 

 
function filterDates(fDates) { 
 
    var oneday = 1000 * 60 * 60 * 24, 
 
    tooFarFuture = oneday * 30, 
 
    lastdate = null; 
 

 
    return fDates.filter(function(fitem, i) { 
 
    var itemdate = new Date(fitem[0]); 
 
    if (lastdate) { 
 
     /* Allow Repeated Date */ 
 
     if (itemdate == lastdate) return false; 
 
     /* List out Backward and Too Far Date */ 
 
     if (itemdate < lastdate || itemdate - lastdate > tooFarFuture) return true; 
 
     /* If date is not today/tomorrow to lastdate i.e a date gap */ 
 
     /* Try to find a more closer date */ 
 
     if (itemdate - lastdate > oneday) { 
 
     for (var j = i + 1; j < fDates.length; j++) { 
 
      var testdate = new Date(fDates[j][0]); 
 
      if (testdate > lastdate && testdate < itemdate) return true; 
 
     } 
 
     } 
 
    } 
 
    lastdate = itemdate; 
 
    }); 
 
}

+0

Comment savoir laquelle de ces séquences est correcte? Votre code indique que la séquence la plus longue est celle qui n'est pas à sa place. Mine (Rosetta's) indique que la séquence la plus courte est hors de propos: '['2015-01-01'], ['2014-01-01'], ['2015-01-02'], ['2014-01 -02 '], [' 2015-01-03 '], [' 2014-01-03 '], [' 2014-01-04 '], [' 2015-01-04 '], [' 2014-01 -05 '], [' 2014-01-06 '], [' 2014-01-07 ']] ' –

+0

Comme la simplicité. Cependant, il suppose les paramètres de ce qui est connu ... c'est-à-dire, qu'une date de plus de 30 est trop loin (quand il peut y avoir 90 jours entre chaque fois qu'ils augmentent) – Trees4theForest

+0

Ensuite, vous pouvez augmenter le 'tooFarFuture' à 90 jours :) –

3

Cette solution utilise la fonction reduce et maintient la date précédemment accepté de faire les comparaisons nécessaires.

var fDates = [['2015-02-03', 'name1'], ['2015-02-04', 'nameg'], ['2015-02-04', 'name5'], ['2015-02-05', 'nameh'], ['1929-03-12', 'name4'], ['2023-07-01', 'name7'], ['2015-02-07', 'name0'], ['2015-02-08', 'nameh'], ['2015-02-15', 'namex'], ['2015-02-09', 'namew'], ['1980-12-23', 'name2'], ['2015-02-12', 'namen'], ['2015-02-13', 'named']], 
 
results = fDates.reduce((acc, c, i, arr) => { 
 
    /* 
 
    * This function finds a potential valid sequence. 
 
    * Basically, will check if any next valid sequence is 
 
    * ahead from the passed controlDate. 
 
    */ 
 
    function sequenceAhead(controlDate) { 
 
    for (var j = i + 1; j < arr.length; j++) { 
 
     let [dt] = arr[j]; 
 
     //The controlDate is invalid because at least a forward date is in conflict with its sequence. 
 
     if (dt > acc.previous && dt < controlDate) return true; 
 
    } 
 
    
 
    //The controlDate is valid because forward dates don't conflict with its sequence. 
 
    return false; 
 
    } 
 
    
 
    let [date] = c; //Current date in this iteration. 
 
    if (i > 0) { // If this is not the first iteration 
 
    if (date === acc.previous) return acc; // Same as previous date are skipped. 
 
    // If the current date is lesser than previous then is out of sequence. 
 
    // Or if there is at least valid sequence ahead. 
 
    if (date < acc.previous || sequenceAhead(date)) acc.results.push(c); 
 
    else acc.previous = date; // Else, this current date is in sequence. 
 
    } 
 
    else acc.previous = date; // Else, set the first date. 
 

 
    return acc; 
 
}, { 'results': [] }).results; 
 

 
console.log(results);
.as-console-wrapper { max-height: 100% !important; top: 0; }

+0

Comment savons-nous laquelle de ces séquences est correcte? Votre code indique que la séquence la plus longue est celle qui n'est pas à sa place. Mine (Rosetta's) indique que la séquence la plus courte est hors de propos: '['2015-01-01'], ['2014-01-01'], ['2015-01-02'], ['2014-01 -02 '], [' 2015-01-03 '], [' 2014-01-03 '], [' 2014-01-04 '], [' 2015-01-04 '], [' 2014-01 -05 '], [' 2014-01-06 '], [' 2014-01-07 ']] ' –

5

Cette solution essaie d'obtenir toutes les séquences valides et renvoie les séquences Longes pour filtrer les pièces en.

Il fonctionne en itérant le tableau donné et vérifie si les valeurs pourraient construire une séquence. Si une valeur est donnée, le résultat de la partie a un prédécesseur valide, le tableau est ajouté avec cette valeur. Sinon, un retour en arrière est effectué et une séquence est recherchée avec un prédécesseur valide.

act. array 
value 7 3 4 4 5 1 23 7 comment 
----- ------------------------ --------------------------- 
    7 7      add array with single value 

    3 7      keep 
      3      add array with single value 

    4 7      keep 
      3 4     add value to array 

    4 7      keep 
      3 4 4    add value to array 

    5 7      keep 
      3 4 4 5   add value to array 

    1 7      keep 
      3 4 4 5   keep 
         1   add array with single value 

    23 7    23  add value to array 
      3 4 4 5 23  add value to array 
         1 23  add value to array 

    7 7    23  keep 
     7     7 fork above, filter for smaller or equal and add value 
      3 4 4 5 23  keep 
      3 4 4 5  7 fork above, filter for smaller or equal and add value 
         1 23  keep 
         1  7 fork above, filter for smaller or equal and add value 

function longestSequences(array, getValue = v => v) { 
 
    return array 
 
     .reduce(function (sub, value) { 
 
      var single = true; 
 

 
      sub.forEach(function (s) { 
 
       var temp; 
 

 
       if (getValue(s[s.length - 1]) <= getValue(value)) { 
 
        s.push(value); 
 
        single = false; 
 
        return; 
 
       } 
 

 
       // backtracking 
 
       temp = s.reduceRight(function (r, v) { 
 
        if (getValue(v) <= getValue(r[0])) { 
 
         r.unshift(v); 
 
         single = false; 
 
        } 
 
        return r; 
 
       }, [value]); 
 

 
       if (temp.length !== 1 && !sub.some(s => s.length === temp.length && s.every((v, i) => getValue(v) === getValue(temp[i])))) { 
 
        sub.push(temp); 
 
       } 
 
      }); 
 

 
      if (single) { 
 
       sub.push([value]); 
 
      } 
 
      return sub; 
 
     }, []) 
 
     .reduce(function (r, a) { 
 
      if (!r || r[0].length < a.length) { 
 
       return [a]; 
 
      } 
 
      if (r[0].length === a.length) { 
 
       r.push(a); 
 
      } 
 
      return r; 
 
     }, undefined); 
 
} 
 

 
function notInSequence(array, getValue = v => v) { 
 
    var longest = longestSequences(array, getValue); 
 
    return array.filter((i => a => a !== longest[0][i] || !++i)(0)); 
 
} 
 

 
var array = [7, 3, 4, 4, 5, 1, 23, 7, 8, 15, 9, 2, 12, 13], 
 
    fDates = [['2015-02-03', 'name1'], ['2015-02-04', 'nameg'], ['2015-02-04', 'name5'], ['2015-02-05', 'nameh'], ['1929-03-12', 'name4'], ['2023-07-01', 'name7'], ['2015-02-07', 'name0'], ['2015-02-08', 'nameh'], ['2015-02-15', 'namex'], ['2015-02-09', 'namew'], ['1980-12-23', 'name2'], ['2015-02-12', 'namen'], ['2015-02-13', 'named']], 
 
    usuallyFailingButNotHere = [['2015-01-01'], ['2014-01-01'], ['2015-01-02'], ['2014-01-02'], ['2015-01-03'], ['2014-01-03'], ['2014-01-04'], ['2015-01-04'], ['2014-01-05'], ['2014-01-06'], ['2014-01-07'], ['2014-01-08'], ['2014-01-09'], ['2014-01-10'], ['2014-01-11']], 
 
    test2 = [['1975-01-01'], ['2015-02-03'], ['2015-02-04'], ['2015-02-04'], ['2015-02-05'], ['1929-03-12'], ['2023-07-01'], ['2015-02-07'], ['2015-02-08']]; 
 

 
console.log(longestSequences(array)); 
 
console.log(notInSequence(array)); 
 

 
console.log(notInSequence(fDates, a => a[0])); 
 

 
console.log(longestSequences(usuallyFailingButNotHere, a => a[0])); 
 
console.log(notInSequence(usuallyFailingButNotHere, a => a[0])); 
 

 
console.log(longestSequences(test2, a => a[0])); 
 
console.log(notInSequence(test2, a => a[0]));
.as-console-wrapper { max-height: 100% !important; top: 0; }

+1

Comment savons-nous laquelle de ces séquences est correcte? Votre code indique que la séquence la plus longue est celle qui n'est pas à sa place. Mine (Rosetta's) indique que la séquence la plus courte est hors de propos: '['2015-01-01'], ['2014-01-01'], ['2015-01-02'], ['2014-01 -02 '], [' 2015-01-03 '], [' 2014-01-03 '], [' 2014-01-04 '], [' 2015-01-04 '], [' 2014-01 -05 '], [' 2014-01-06 '], [' 2014-01-07 ']] ' –

+0

@ עדבלעדברקן, j'ai changé l'algorithme pour un plus fiable. votre tableau mentionné fonctionne maintenant, comme il ressemble. –

+0

(Je me demande si LIS est ce que l'OP veut, cependant, ha - peut-être il y a d'autres contraintes) –

2

Toutes les réponses précédentes se concentrent sur JavaScript et peut-être qu'ils ne fonctionnera pas correctement . J'ai donc décidé d'ajouter une nouvelle réponse qui se concentrait sur Algorithme.

Comme @ Trees4theForest mentionné dans sa question et commentaires, il est à la recherche d'une solution pour Longest Increase Subsequence et out of order dates sont des dates qui ne sont pas plus longue augmentation prévue Subsequence (LIS).

J'ai utilisé la méthode this comme ci-dessous. Du point de vue de l'algorithme, c'est vrai.

function longestIncreasingSequence(arr, strict) { 

    var index = 0, 
     indexWalker, 
     longestIncreasingSequence, 
     i, 
     il, 
     j; 

    // start by putting a reference to the first entry of the array in the sequence 
    indexWalker = [index]; 

    // Then walk through the array using the following methodolgy to find the index of the final term in the longestIncreasing and 
    // a sequence (which may need altering later) which probably, roughly increases towards it - http://en.wikipedia.org/wiki/Longest_increasing_subsequence#Efficient_algorithms 
    for (i = 1, il = arr.length; i < il; i++) { 

     if (arr[i] < arr[indexWalker[index]]) { 

      // if the value is smaller than the last value referenced in the walker put it in place of the first item larger than it in the walker 
      for (j = 0; j <= index; j++) { 

       // As well as being smaller than the stored value we must either 
       // - be checking against the first entry 
       // - not be in strict mode, so equality is ok 
       // - be larger than the previous entry 
       if (arr[i] < arr[indexWalker[j]] && (!strict || !j || arr[i] > arr[indexWalker[j - 1]])) { 
        indexWalker[j] = i; 
        break; 
       } 
      } 

      // If the value is greater than [or equal when not in strict mode) as the last in the walker append to the walker 
     } else if (arr[i] > arr[indexWalker[index]] || (arr[i] === arr[indexWalker[index]] && !strict)) { 
      indexWalker[++index] = i; 
     } 

    } 

    // Create an empty array to store the sequence and write the final term in the sequence to it 
    longestIncreasingSequence = new Array(index + 1); 
    longestIncreasingSequence[index] = arr[indexWalker[index]]; 


    // Work backwards through the provisional indexes stored in indexWalker checking for consistency 
    for (i = index - 1; i >= 0; i--) { 

     // If the index stored is smaller than the last one it's valid to use its corresponding value in the sequence... so we do 
     if (indexWalker[i] < indexWalker[i + 1]) { 
      longestIncreasingSequence[i] = arr[indexWalker[i]]; 

      // Otherwise we need to work backwards from the last entry in the sequence and find a value smaller than the last entry 
      // but bigger than the value at i (this must be possible because of the way we constructed the indexWalker array) 
     } else { 
      for (j = indexWalker[i + 1] - 1; j >= 0; j--) { 
       if ((strict && arr[j] > arr[indexWalker[i]] && arr[j] < arr[indexWalker[i + 1]]) || 
        (!strict && arr[j] >= arr[indexWalker[i]] && arr[j] <= arr[indexWalker[i + 1]])) { 
        longestIncreasingSequence[i] = arr[j]; 
        indexWalker[i] = j; 
        break; 
       } 
      } 
     } 
    } 

    return longestIncreasingSequence; 
} 

Avec la méthode ci-dessus, nous pouvons trouver des dates qui est hors d'usage comme ci-dessous:

// Finding Longest Increase Subsequence (LIS) set 
var _longestIncreasingSequence = longestIncreasingSequence(fDates.map(([date]) => date)); 

// Out of order dates 
var result = fDates.filter(([date]) => !_longestIncreasingSequence.includes(date)); 

Online demo(jsFiddle)

+0

"Toutes les réponses précédentes se concentrent sur JavaScript et peuvent ne pas fonctionner correctement." Pas correct - ma réponse (et maintenant aussi celle de Nina) utilise LIS –

1

Résumé de votre question Si je comprends bien votre question, vous essayez d'identifier les entrées de tableau qui ne suivent pas un ordre chronologique basé sur la valeur de la propriété heure/date.

Solution Convertir la chaîne de date/heure dans un horodatage UNIX (nombre de secondes écoulées depuis 01/jan/1970 à 00:00:00)

En utilisant une boucle, nous pouvons stocker la valeur par rapport à une lecture précédente par itenary, si la valeur est négative, cela indiquerait une erreur dans le laps de temps, si la valeur est positive, il indiquerait la commande est valide

Lorsque négatif, nous pouvons créer un tableau pour indiquer la position du tableau de référence et ses valeurs vous permettant de revenir au tableau d'origine et d'examiner les données.

Exemple de code

var arrData = [ 
 
    {date: '2015-02-03', value:'name1'}, 
 
    {date: '2015-02-04', value:'nameg'}, 
 
    {date: '2015-02-04', value:'name5'}, 
 
    {date: '2015-02-05', value:'nameh'}, 
 
    {date: '1929-03-12', value:'name4'}, 
 
    {date: '2023-07-01', value:'name7'}, 
 
    {date: '2015-02-07', value:'name0'}, 
 
    {date: '2015-02-08', value:'nameh'}, 
 
    {date: '2015-02-15', value:'namex'}, 
 
    {date: '2015-02-09', value:'namew'}, 
 
    {date: '1980-12-23', value:'name2'}, 
 
    {date: '2015-02-12', value:'namen'}, 
 
    {date: '2015-02-13', value:'named'} 
 
]; 
 

 
var arrSeqErrors = []; 
 
function funTestDates(){ 
 
    var intLastValue = 0, intUnixDate =0; 
 
    for (x = 0; x <= arrData.length-1; x++){ 
 
    intUnixDate = Date.parse(arrData[x].date)/1000; 
 
    var intResult = intUnixDate - intLastValue; 
 
    if (intResult < 0){ 
 
     console.log("initeneration: " + x + " is out of sequence"); 
 
     arrSeqErrors.push (arrData[x]); 
 
    } 
 
    intLastValue = intResult; 
 
    } 
 
    console.log("Items out of sequence are:"); 
 
    console.log(arrSeqErrors); 
 
} 
 

 
funTestDates();

+0

Vous remarquerez que j'ai donné les étiquettes de tableau telles que Date et Valeur pour que ce petit morceau de code fonctionne, je pense que cela peut facilement être inséré dans vos résultats si besoin d'être – DataCure

+0

Une approche simple - mais peut-être trop simpliste? Comme il ne considère que la relation du nombre suivant au précédent, il passe incorrectement le 2023-07-01 et les drapeaux 2015-02-07. – Trees4theForest

+0

Essayez-vous de trouver une séquence différente et si oui, quel type de séquence. En termes de valeurs stockées, vous pouvez ajouter un -1 sur le X lorsque vous placez la valeur dans le tableau arrSeqErrors – DataCure

2

ici est une solution simple auto-explicative. J'espère que cela vous aidera.

const findOutOfSequenceDates = items => { 
 
    items = items.map(d => d); 
 

 
    const sequence = [], outOfsequence = []; 
 
    sequence.push(items.shift()); 
 

 
    const last = ind => sequence[sequence.length - ind][0]; 
 

 
    items.forEach(item => { 
 
     const current = new Date(item[0]); 
 

 
     if (current >= new Date(last(1))) { 
 
      sequence.push(item); 
 
     } else if (current >= new Date(last(2))) { 
 
      outOfsequence.push(sequence.pop()); 
 
      sequence.push(item); 
 
     } else { 
 
      outOfsequence.push(item); 
 
     } 
 
    }); 
 

 
    return outOfsequence; 
 
}; 
 

 
var fDates = [ 
 
    ['2015-02-03', 'name1'], 
 
    ['2015-02-04', 'nameg'], 
 
    ['2015-02-04', 'name5'], 
 
    ['2015-02-05', 'nameh'], 
 
    ['1929-03-12', 'name4'], 
 
    ['2023-07-01', 'name7'], 
 
    ['2015-02-07', 'name0'], 
 
    ['2015-02-08', 'nameh'], 
 
    ['2015-02-15', 'namex'], 
 
    ['2015-02-09', 'namew'], 
 
    ['1980-12-23', 'name2'], 
 
    ['2015-02-12', 'namen'], 
 
    ['2015-02-13', 'named'], 
 
]; 
 
console.log(findOutOfSequenceDates(fDates));