02-21-2013 06:37 AM
I am using a for loop to step through the elements in a channel and look for a rising or falling edge. It works fine.
What I have noticed though is that I can hugely (~100x) speed up the operation by first scaling the channel with a factor of 1:
chnlinscale("/[1]","/[1]",1)
Has anybody else seen this or can anybody explain this to me please?
Thank you,
Martin
02-21-2013 08:21 AM
Hello Martin,
The reason can be the load behavior of the NAVIGATOR. DIAdem supports 3 different types. You find detailed information in the DIAdem help. In your case you can use "Always load ..." or "Load bulk data on first access".
By the way, I'm sure that you already know that the fastest access to a channel value is the Data-API. Here is a small example:
dim oChn set oChn = Data.GetChannel("myGroup/myChannel") oChn(i) = myNewValue
Greetings
Walter
02-21-2013 09:54 AM
Hi Martin,
You can speed this up even more by using the ChnCalculate() or ChnFind() functions to identify or find the feature you're interested in. These commands execute MUCH faster than an interpreted VBScript loop over all the channel values.
Brad Turpin
DIAdem Product Support Engineer
National Instruments
02-22-2013 02:29 AM
Hi there,
Thank you both for the help, it is very much appreciated. I had forgotten about the bulk load options and the effect that it has, I couldn't understand what was happening.
I tried running some different rising/falling edge detect algorithms on a channel I had. It was 900,000 elements long with about 850 rising and 850 falling edges.
I found the edges using an elseif statement to step through and compare each new value with the last, and with the ChnFind fucntion. I then also used a select statement and another elseif statement where I knew the high and low values were 1-0 so it made the calculation simpler.
What I found is that they were all really fast, looping through the elements with the elseif took about 2.3s, using ChnFind about 2.1s, this is on my standard work laptop. The select statement with 1-0 transition was the fastest, taking only 1.3s.
I'm very happy with these speeds but if there are ways I can improve this I'd be pleased to hear as it is something I do quite a lot on much bigger datasets.
Thanks again,
Martin
set chn = Data.GetChannel("[1]/[1]") stopwatchreset() 'Run one of the methods and check the time 'using_elseif() '2.3s 'using_chnfind() '2.1s' 'using_elseif_one_zero() '1.5s using_select_one_zero() '1.3s Call MsgBoxDisp("Elapsed: "+Str(Stopwatch(1),"d.dd")+"s") redim preserve result(1,j-1) call arraytochannels(result,array("/rising","/falling"),true) '---------------------- sub using_chnfind() dim edge: edge=1 do while edge < chn.size and edge>0 edge = ChnFind("Ch(""[1]/[1]"")>0.5",edge) if edge >0 then result(RISING,j) = edge edge = ChnFind("Ch(""[1]/[1]"")<0.5",edge) if edge > 0 then result(FALLING,j) = edge j=j+1 end if loop end sub sub using_elseif dim i,started : started = false for i=2 to chn.Size if chn(i) > 0.5 and chn(i-1) < 0.5 then 'rising edge result(RISING,j) = i started = true elseif chn(i) < 0.5 and chn(i-1) > 0.5 and started = true then 'falling edge result(FALLING,j)=i j=j+1 end if next end sub sub using_elseif_one_zero dim dv,i,started : started = false for i = 2 to chn.Size dv = chn(i) - chn(i-1) if dv = 1 then 'rising edge result(RISING,j) = i started = true elseif dv = -1 and started = true then 'falling edge result(FALLING,j)=i j=j+1 end if next end sub sub using_select_one_zero dim i,dv,started : started = false for i = 2 to chn.Size dv = chn(i) - chn(i-1) select case dv case 1 'rising edge result(RISING,j) = i started = true case -1 'falling edge if started then result(FALLING,j)=i j=j+1 end if case else end select next end sub
02-22-2013 02:46 AM
I meant to say, I realise the benefit of the ChnFind function is probably not going to be seen on such a simple search criteria.
02-22-2013 11:34 AM
Hi Martin,
Those benchmarks are very interesting. I would have guessed the ChnFind() function would have been much faster. How many data points do you have per cycle (assuming the time between nearest rising edges is one cycle)? I think that's the critical metric, not the length of the channel. I would guess that ChnFind() would be much faster as the number of points per cycle got bigger than 100, say.
Brad Turpin
DIAdem Product Support Engineer
National Instruments