# Current js code ```javascript= const fs = require('fs') var data =[] var carsEvents=[] var carsIntervals=[] var sortedCarsIntervalAndWeights=[] var carMap = new Map() var carCustomerMap = new Map() var customersEvents=[] var customersVisits=[] var car_id, place_id, event_type_id var customer_id, place_id, event_type_id var customer_id0=0 var t, dt; var car_id0=0 const NumOf = 50; const tau=60*60 //sec = 60 minutes -- edge time diff beetwen separated time intervals const downScalingFactor=10 // weights of non repeated car-person interval cooccurences must be scaled down by this factor const mParameter=8 // algorithm parameter for rising weights in repeated car-person interval cooccurences const minWeightEdge=0.1 // algorithm parameter - edge for separating significant weights from non-significant const weigthDempherFactor=0.95 const defaultShiftFromStartToPrk=1.5*60 // default start parameter for missed events Begin or Prk const defaultPrkDuration=3*60 // default Prk duration parameter for missed event Prk const defaultShiftFromPrkToExit=30 // default time shift from Prk to Exit for missed event Prk or Exit const startDate = '2021-03-09' let startTms = Date.parse('2021-03-09T00:00:00Z'); let startTs = startTms/1000; function msToTime(s) { // Pad to 2 or 3 digits, default is 2 var pad = (n, z = 2) => ('00' + n).slice(-z); return pad(s/3.6e6|0) + ':' + pad((s%3.6e6)/6e4 | 0) + ':' + pad((s%6e4)/1000|0) /* + '.' + pad(s%1000, 3)*/; } var filetxt = fs.readFileSync('./car_event_from_sql2.txt')+''; events = filetxt.split(/\r?\n/) var ic=0; events.forEach( line => { data=line.split(/\s+/) car_id = Number(data[0]); place_id = Number(data[1]); event_type_id = Number(data[2]); t = Number(data[3]); dt = Number(data[4]); if(car_id0 != car_id){ car_id0 = car_id ic++; carsEvents[ic]=[] } carsEvents[ic].push([car_id, place_id, event_type_id, t, dt]) // console.log( car_id, msToTime(t*1000), new Date(startTms+t*1000)) } ) for(var i=1; i< ic; i++) // i - internal car number for this script { let events = carsEvents[i] let el=events.length for(let e=0;e<el;e++) { t = events[e][3] dt = events[e][4] let t1=t+dt; let t2 = Number.MAX_VALUE; if(e+1<el)t2 = events[e+1][3] diff = t2 - t1 events[e].push(diff) } } var I=[] var car for(var i=1; i< ic; i++) // i - car number { let events = carsEvents[i] // events only for car i let el=events.length car=carsEvents[i][0] // console.log(i+`-----car_id=${car[0]}-----------------------------------------`) let n=0; carsIntervals[i]=[] let key=car[0] let value=[] // sortedCarsIntervalAndWeights[i]=[] // carsIntervals[i].push(car[0]) let currentCarEventsEnded=false let e=0; // event number for the sequence of events of car i while(!currentCarEventsEnded) { I=[] // new Interval let intervalClosed=false while(!intervalClosed) { p= events[e][1] pt= events[e][2] t = events[e][3] dt = events[e][4] diff=events[e][5] I.push([p, pt, t,dt]) // push data for current Interval e++ currentCarEventsEnded = (e>=el) intervalClosed = (diff>=tau)|currentCarEventsEnded } let intervalFunctionData = Irecovery() let carWithIntervalFunctionData = [car[0],intervalFunctionData] value.push(intervalFunctionData) carsIntervals[i].push(carWithIntervalFunctionData) sortedCarsIntervalAndWeights.push(carWithIntervalFunctionData) // copy for sorting } carMap.set(key,value); } sortedCarsIntervalAndWeights.sort((a,b)=> a[1][0][0]-b[1][0][0]) //sort by begin time /* let c1ints=(carMap.get(16291)) console.log(c1ints[0]) console.log(c1ints[1]) console.log(c1ints[2]) for (var key of carMap.keys()) { console.log(key, typeof key); } console.log('****************car Map**********************************************') console.log(carMap) */ /* console.log('****************sorted cars by start**********************************************') for(var i=0; i< sortedCarsIntervalAndWeights.length; i++) // i - car number { let begintime=sortedCarsIntervalAndWeights[i][1][0][0]; let endIndex=sortedCarsIntervalAndWeights[i][1][0].length -1; let endtime=sortedCarsIntervalAndWeights[i][1][0][endIndex] console.log(sortedCarsIntervalAndWeights[i][0], sortedCarsIntervalAndWeights[i][1][0], 'begin:'+ begintime, 'end:'+ endtime) } */ /* console.log('++++++++++++++++++cars by number+++++++++++++++++++++++++++++++++++++++++++++') for(var i=1; i< ic; i++) // i - car number { for(var j=0; j< carsIntervals[i].length; j++) { let beginIndex=0; let endIndex=carsIntervals[i][j][1][0].length -1; console.log(carsIntervals[i][j], 'begin:'+ carsIntervals[i][j][1][0][beginIndex], 'end :'+ carsIntervals[i][j][1][0][endIndex]) } } */ function Irecovery(){ let Imin=Number.MAX_VALUE; let Imax=0 let ets=[] let t1=0; let dt=0; let t2=0; for(let i=0; i<I.length;i++) { Ie=I[i] t1=Ie[2] dt=Ie[3] t2=t1+dt if(Imin>t1)Imin=t1 if(Imax<t2)Imax=t2 ets.push(Ie[1]) // event type places } let etS = new Set(ets); let etss = Array.from(etS); let timepoints =[] let weights =[] if(etS.size==1) { let pt=etss[0]; if(pt==2) //if only Begins points { let w=0; for(let i=0; i<I.length;i++) { Ie=I[i] t1=Ie[2] timepoints.push(t1); w+=0.01 weights.push(w) } //add default Prk and Exit timepoints and weights Ie=I[I.length-1] t1=Ie[2]+defaultShiftFromStartToPrk timepoints.push(t1); weights.push(0.75) t1 += defaultPrkDuration timepoints.push(t1); weights.push(0.25) t1 += defaultShiftFromPrkToExit timepoints.push(t1); weights.push(0.01) } // else if(pt==4) //if only Exits points { let w=0; //add default Begin and Prk timepoints and weights t1 = - defaultShiftFromStartToPrk - defaultPrkDuration - defaultShiftFromPrkToExit + Imin timepoints.push(t1); weights.push(0.01) t1 += defaultShiftFromStartToPrk timepoints.push(t1); weights.push(0.75) t1 += defaultPrkDuration timepoints.push(t1); weights.push(0.25) for(let i=0; i<I.length;i++) { Ie=I[i] t1=Ie[2] //if(!t1)console.log(Ie) timepoints.push(t1); w=0.01 weights.push(w) } } if(pt==6) //if only Prk points { let w=0; //add default Begin and Prk timepoints and weights t1 = - defaultShiftFromStartToPrk + Imin timepoints.push(t1); weights.push(0.01) for(let i=0; i<I.length;i++) { Ie=I[i] t1=Ie[2] dt=Ie[3] timepoints.push(t1); weights.push(0.9) t1 +=dt timepoints.push(t1); weights.push(0.75) } t1 = Imax + defaultShiftFromPrkToExit timepoints.push(t1); weights.push(0.01) } } if(etS.size==2) { let pt1=etss[0]; let pt2=etss[1]; if(pt1==2 && pt2==4 || pt1==4 && pt2==2) //if only Begins and Exit points { let t1 = Imin let tprk1 = Imin +defaultShiftFromStartToPrk let tprk2 = -defaultShiftFromPrkToExit + Imax let t2 = Imax timepoints.push(t1); weights.push(0.01) timepoints.push(tprk1); weights.push(0.75) timepoints.push(tprk2); weights.push(0.25) timepoints.push(t2); weights.push(0.01) } if(pt1==2 && pt2==6) //if only Begins and Prk points { let w=0; for(let i=0; i<I.length;i++) { Ie=I[i] pt=Ie[1] t1=Ie[2] dt=Ie[3] if(pt==2) //if it is Begin { timepoints.push(t1); w+=0.01 weights.push(w) } if(pt==6) //if it is Prk { timepoints.push(t1); weights.push(0.9) t1+=dt timepoints.push(t1); weights.push(0.75) } } t1 = timepoints[timepoints.length-1]; t1 += defaultShiftFromPrkToExit; timepoints.push(t1); weights.push(0.01) } if(pt1==6 && pt2==2) //if only Prk and Begins after points = Prk Exit ? { let w=0; let t1 = -defaultShiftFromStartToPrk + Imin timepoints.push(t1); weights.push(0.01) for(let i=0; i<I.length;i++) { Ie=I[i] pt=Ie[1] t1=Ie[2] dt=Ie[3] if(pt==2) //if it is Begin { timepoints.push(t1); weights.push(0.01) } if(pt==6) //if it is Prk { timepoints.push(t1); weights.push(0.9) t1+=dt timepoints.push(t1); weights.push(0.75) } } t1 = timepoints[timepoints.length-1]; t1 += defaultShiftFromPrkToExit; timepoints.push(t1); weights.push(0.01) } if(pt1==6 && pt2==4) //if only Prk and Exit { let w=0; let t1 = -defaultShiftFromStartToPrk + Imin timepoints.push(t1); weights.push(0.01) for(let i=0; i<I.length;i++) { Ie=I[i] pt=Ie[1] t1=Ie[2] dt=Ie[3] if(pt==4) //if it is Exit { timepoints.push(t1); weights.push(0.01) } if(pt==6) //if it is Prk { timepoints.push(t1); weights.push(0.9) t1+=dt timepoints.push(t1); weights.push(0.75) } } } if(pt1==4 && pt2==6) //if only Prk and Exit { for(let i=0; i<I.length;i++) { Ie=I[i] pt=Ie[1] t1=Ie[2] dt=Ie[3] if(pt==4) //if it is Exit { timepoints.push(t1); weights.push(0.01) } if(pt==6) //if it is Prk { timepoints.push(t1); weights.push(0.9) t1+=dt timepoints.push(t1); weights.push(0.75) } } } } if(etS.size==3) { let pt1=etss[0]; let pt2=etss[1]; let pt3=etss[2]; if(pt1==2||pt1==4) //if Begins then Prk then Exit points { for(let i=0; i<I.length;i++) { Ie=I[i] pt=Ie[1] t1=Ie[2] dt=Ie[3] if(pt==2) //if it is Begin { timepoints.push(t1); weights.push(0.01) } if(pt==6) //if it is Prk { timepoints.push(t1); weights.push(0.9) t1+=dt timepoints.push(t1); weights.push(0.75) } if(pt==4) //if it is Exit { timepoints.push(t1); weights.push(0.01) } } } if(pt1==6) //if Begins then Prk then Exit points { let w=0; let t1 = -defaultShiftFromStartToPrk + Imin timepoints.push(t1); weights.push(0.01) for(let i=0; i<I.length;i++) { Ie=I[i] pt=Ie[1] t1=Ie[2] dt=Ie[3] if(pt==2) //if it is Begin { timepoints.push(t1); weights.push(0.01) } if(pt==6) //if it is Prk { timepoints.push(t1); weights.push(0.9) t1+=dt timepoints.push(t1); weights.push(0.75) } if(pt==4) //if it is Exit { timepoints.push(t1); weights.push(0.01) } } } } // console.log(I) // console.log(`Imin=${Imin} Imax=${Imax} ets=${ets} etS.size=${etS.size} etss=${etss}`) // console.log([timepoints,weights]) return [timepoints,weights] } var filetxt = fs.readFileSync('./customer_events_from_sql2.txt')+''; events = filetxt.split(/\r?\n/) var ip=0; events.forEach( line => { data=line.split(/\s+/) customer_id = Number(data[0]); place_id = Number(data[1]); event_type_id = Number(data[2]); t = Number(data[3]); dt = Number(data[4]); if(customer_id0 != customer_id){ customer_id0 = customer_id ip++; customersEvents[ip]=[] } customersEvents[ip].push([customer_id, place_id, event_type_id, t, dt]) } ) for(var i=1; i<= ip; i++) // i - internal customer number for this script { let events = customersEvents[i] let el=events.length for(let e=0;e<el;e++) { t = events[e][3] dt = events[e][4] let t1=t+dt; let t2 = Number.MAX_VALUE; if(e+1<el)t2 = events[e+1][3] diff =t2-t1 events[e].push(diff) } } var I=[] var customer for(var i=1; i<= ip; i++) // i - customer number { let events = customersEvents[i] let el=events.length customer=customersEvents[i][0] // console.log(i+`-----customer_id=${customer[0]}-----------------------------------------`) let n=0; customersVisits[i]=[] customersVisits[i].push(customer[0]) let customerEventsEnded=false let e=0; while(!customerEventsEnded) { I=[] // new Interval let intervalClosed=false while(!intervalClosed) { p= events[e][1] pt= events[e][2] t = events[e][3] dt = events[e][4] diff=events[e][5] I.push([p, pt, t,dt]) // push data for current Interval e++ customerEventsEnded = (e>=el) intervalClosed = (diff>=tau)|customerEventsEnded } let intervalData = I customersVisits[i].push(intervalData) } } for(let i=1; i<=ip; i++) // i - customer number { let carsWeightsMap = new Map(); let carsRepeatCountMap = new Map(); // console.log("----customer:",customersVisits[i][0], "customer number of intervals="+(customersVisits[i].length-1)) for(let j=1; j< customersVisits[i].length; j++) // j - number of customer visits ordered by begin time { let custbeginIndex=0; let pib=customersVisits[i][j][custbeginIndex][2] //begin of customer visit let pin=customersVisits[i][j].length; // customer visit number of events let custendIndex=pin-1; let pie=customersVisits[i][j][custendIndex][2] //end of customer visit let k = 0|0; // k - index of car interval let k0 = 0|0; // k0 - left index of range let k1 = (sortedCarsIntervalAndWeights.length-1)|0 // k1 - right index of range let km = (k0+k1)>>1 // km - mid index of range let midtime = sortedCarsIntervalAndWeights[km][1][0][0]; // indexed mid of time range while (k1 - k0 > 1){// Iterate moving midtime+tau to pib while left not meets right km = (k0 + k1)>>1; midtime = sortedCarsIntervalAndWeights[km][1][0][0]; if (midtime + tau < pib) k0 = km + 1; else k1 = km - 1; } k=k0 let begintime = sortedCarsIntervalAndWeights[k][1][0][0]; //begin of car's current time interval let endtime = 0.0; do { let car_id = sortedCarsIntervalAndWeights[k][0] let numberOfPoints = sortedCarsIntervalAndWeights[k][1][0].length let endIndex = numberOfPoints -1; endtime = sortedCarsIntervalAndWeights[k][1][0][endIndex] //end of car's current time interval let Wm = 0; let Tm = 0; // future person time of max weight for car number k let T0 = 0; // future car left time of max weight for car number k let wT0 = 0; // future car left time weight for max weight for car number k if(pib>begintime && pie<endtime) // condition that must be meet for person and current car interval { Wm=0; // future max weight for car number k Tm=0; for(let l = 0; l < pin; l++) //l - index of event list of one interval of customer { let pers_t = customersVisits[i][j][l][2] // time of event in current customer interval for(let m = 0; m < endIndex; m++) //m - index of timepoints of one interval of car k (current car) { // search subinterval [t0,t1] for customer time pers_t let t0 = sortedCarsIntervalAndWeights[k][1][0][m] let t1 = sortedCarsIntervalAndWeights[k][1][0][m+1] if(pers_t<t0 || pers_t>=t1)continue; // linear interpolation of time points weights let h = t1 - t0 let x = pers_t - t0 let _x = t1 - pers_t let w0 = sortedCarsIntervalAndWeights[k][1][1][m] let w1 = sortedCarsIntervalAndWeights[k][1][1][m+1] w = (w0* _x + w1*x)/h/downScalingFactor // selecting maximal value of weights w for current car interval and current customer interval if(Wm<w){ T0 = t0 // debugging and control variables Tm = pers_t // debugging and control variables wT0 = w0 // debugging and control variables Wm = w; } } } let carPersCrossCount=0 if(Wm>0.01) { let carRepeatCount = carsRepeatCountMap.get(car_id) if(!carRepeatCount) carsRepeatCountMap.set(car_id, 1) else { carPersCrossCount = carRepeatCount + 1; carsRepeatCountMap.set(car_id, carPersCrossCount) } // console.log(car_id, wT0.toPrecision(2), Wm.toPrecision(2), "delta=" + (Tm-T0).toPrecision(4), new Date(startTms+Tm*1000)) let carW = carsWeightsMap.get(car_id) if(!carW) carsWeightsMap.set(car_id, Wm) else { let newWeight= Math.max(1-(1-carW)**mParameter, 1-(1-Wm)**mParameter) carsWeightsMap.set(car_id, newWeight ) for (var [c, w] of carsWeightsMap) { let cRC = carsRepeatCountMap.get(c) if(newWeight <= 0.9) { if(carPersCrossCount <= cRC) continue // for low weight compare it's count with current carPersCrossCount if( newWeight < w ) continue // do not dempfer weights if car number of repeats greater or equal carPersCrossCount } // newWeight > 0.9 if( newWeight >=w ) continue ; // do not dempfer high weight if it is not enough high w *= weigthDempherFactor carsWeightsMap.set(c,w) // console.log(c + ' = ' + w); } } } } k++; // next car interval begintime = sortedCarsIntervalAndWeights[k][1][0][0]; // next begin of car's time interval } while(begintime<pie) //next customer Visit } if(customersVisits[i].length-1 <2) continue; // number of person inervals >=2 for repeated visits let carsWeightsSortedByWeights = [...carsWeightsMap].sort((a, b) => b[1]-a[1]) if(carsWeightsSortedByWeights.length==0) continue; let item=carsWeightsSortedByWeights[0]; let car_id= item[0] let Weight= item[1] if(Weight<minWeightEdge) continue customer =customersVisits[i][0] //console.log(`======cars weight Map===in relation to customer ${customer}===== number of customer petrol station visits= ${(customersVisits[i].length-1)}=======================`) for(let q=0; q<carsWeightsSortedByWeights.length; q++) { item=carsWeightsSortedByWeights[q]; Weight= item[1] if(Weight<minWeightEdge) break car_id = item[0] let wp = Weight.toPrecision(3) let count = carsRepeatCountMap.get(car_id); console.log(`${customer}, ${car_id}, ${wp} count=${count}`) let customersAndWeights = carCustomerMap.get(car_id) if(!customersAndWeights){ var CW_Arr0 = [] CW_Arr0.push([customer, Weight ]) carCustomerMap.set(car_id, CW_Arr0 ) } else { var CW_Arr = Object.values(customersAndWeights) CW_Arr.push([customer, Weight ]) carCustomerMap.set(car_id, CW_Arr ) } } //next customer } console.log(`----------------------------------------------------------------------------------------------------------------------------------------------------`) console.log(`--------------------------car_id -> customer_id --> weight ----------------------------------------------------------------------------------------`) for (let [key, value] of carCustomerMap) { value.sort((a, b) => b[1]-a[1]) } let carCustomersSortedByCar = [...carCustomerMap].sort((a, b) => a[0]-b[0]) for(let q=0; q<carCustomersSortedByCar.length; q++) { item=carCustomersSortedByCar[q]; //Weight= item[1] // if(Weight<minWeightEdge) break car_id = item[0] let CW_Arr = item[1] for(let p=0; p<CW_Arr.length; p++) { let pair = CW_Arr[p] let customer = pair[0] let Weight = pair[1] let wp = Weight.toPrecision(3) console.log(`${car_id}, ${customer}, ${wp}`) } } //let carsWeightsSortedByWeights = [...carCustomerMap].sort((a, b) => b[1]-a[1]) //console.log( carCustomerMap) ```