High pass filter of 0.01 Hz for EEG slow drifts

I am trying to make a high pass filter for electroencephalographic (EEG) datasets, in order to get rid of very slow drifts. However frequencies around 0.3 Hz are very important for the research these data serve.

I use Matlab and I tried various things. It seems that a very low dB attenuation, of 3 dB is fine with FIR filters. For example I used that:

h=fdesign.highpass('Fst,Fp,Ast,Ap',0.005,0.01,3,1,250); % i needed to cut
d=design(h,'butter');
fvtool(d)


However this filter makes a dc drift at the start of the data and I would not wish to loose these first datapoints.

I have read through your pages that a clever idea is to design a low pass filter that later I would subtract from the real data. I did it with an equiripple filter and it worked but left a baseline lift. I do not want to run now average removal as this is in a next step in the analysis protocol.

Any suggestions?

• So the problem is just the initial response of the filter? Is this prerecorded data that you can just prepend with zeros or is it realtime? – endolith Oct 20 '11 at 15:43
• The lowpass-and-subtract approach will also suffer from the problem you're seeing. The issue is that every filter has delay. Filters with sharp cutoffs like the one you want can have very long delays. I'm not sure why you would do average removal next; the DC gain of the filter that you showed is zero, so there will be no appreciable average to remove (except for the transient period at the start of the output due to the filter's delay). – Jason R Oct 21 '11 at 13:17

You're asking for a time machine: in order to avoid the DC bump at $t=0$, you need to know the state of the filter as if it had been running before the recording ever began. That's not going to happen no matter what kind of filter you use.

Here's a trick which may come in handy for you. Let's say you have an $N$-tap FIR filter (or an IIR filter whose impulse response decays adequately to 0 after $N$ samples). Take the first $N$ samples of your signal, reverse them, and prepend that to the start of your signal. In effect, we're defining a new signal $g(t)=g(-t)=f(t)$ for the purposes of filtering. When you filter that, the filter state will have already been "primed" with the initial signal: delete the first $N$ samples of the output, and the DC bump should have hopefully gone away.

Needless to say, there are numerous gotchas with that scheme — for starters, it's harder to do for realtime processing, and if the signal derivative is high at $t=0$, you are still going to have trust issues with the first few samples. But it should get rid of the bump.

Take a look at the filtfilt function. It gives zero-phase response and a perfect step response. Especially, the step response property of the filtfilt filtering may solve your problem.

I did the trick Mr rtollert explained and thought it was the best I could do.

If you go down the route of continuous sampling/hardware compensation, then efficiency might make you interested in DC blockers as described by Randy Yates and Richard Lyons in dsp Tips & Tricks March 2008

I tried something that worked out well- for the specified amplifier. the matlab code is here: https://sites.google.com/site/marialstavrinou/home/dc-offset-removal-filter-in-matlab.

You don't care about absolute DC value, correct?

Why not just add a static offset to your data so that the first data point is at zero?

Sure, you would have to add the offset to every datapoint, but it would completely avoid the big step-response issues you are having with the filter.

Effectively the filter starts up initialized to zero. Therefore, when your data begins, the filter sees a big stair-step from zero to whatever DC level you have.

Just add offset to remove the stair-step.

Why not to do average removal? The later step which does it "again" just doesn't have effect (it would be substracting zero).

• This is more of a query, and not really an answer to the question. It might have been appropriate as a comment at one point, although the question is so old it just seems pointless at this juncture. – Sam Maloney May 14 '13 at 20:19