<p>Let's say that a class has a <code>public int counter</code> field that is accessed by multiple threads. This <code>int</code> is only incremented or decremented.</p>

<p>To increment this field, which approach should be used, and why?</p>

<ul>
<li><code>lock(this.locker) this.counter++;</code>,</li>
<li><code>Interlocked.Increment(ref this.counter);</code>,</li>
<li>Change the access modifier of <code>counter</code> to <code>public volatile</code>.</li>
</ul>

<p>Now that I've discovered <code>volatile</code>, I've been removing many <code>lock</code> statements and the use of <code>Interlocked</code>. But is there a reason not to do this?</p>

Interlocked functions do not lock.  They are atomic, meaning that they can complete without the possibility of a context switch during increment.  So there is no chance of deadlock or wait.
I would say that you should always prefer it to a lock and increment.
Volatile is useful if you need writes in one thread to be read in another, and if you want the optimizer to not reorder operations on a variable (because things are happening in another thread that the optimizer doesn't know about).  It's an orthogonal choice to how you increment.
This is a really good article if you want to read more about lock-free code, and the right way to approach writing it
http://www.ddj.com/hpc-high-performance-computing/210604448