Question: I've been writing in Java and C# for a while, but I'm having a hard time identifying places where using a custom annotation would be advantageous.

I can see that JUnit uses annotations in test classes to identify the order it should run the methods in the test classes, which obviates the need for a configuration of some sort. 

What are other examples of problems that annotations solve elegantly?

Answer: 
Depending on the annotations you use and how you run JUnit, JUnit scans the classpath and runs everything with the proper annotations (or, in the old school versions, that implemented a certain interface)

You're right in the sense that annotations are mostly useful for configuration - they're essentially metadata about the method/class. Here's an example from my work - for some reason I can't remember, we needed to dump objects to a log, but we wanted to filter some of attributes. We made a `Loggable` annotation that could be applied to individual getters or a class, we then used reflection to determine what to dump and what not to.

I would venture a guess that anything you can do with an annotation you could do with some sort of configuration file. Some annotations are basically formalized comments (e.g., @Deprecated). So the fact you can't come up with common cases isn't really surprising.
I've been experimenting with using annotations to give executable specifications to code and generating unit tests for my [algebra project](https://github.com/mdgeorge4153/jalgebra). For example, I have an interface with a method to add two objects together, and the properties you would expect from additions are marked as annotations:

```
interface Group<E> extends Set<E> {
  @Commutative @Associative @Identity("zero") @Inverse("neg")
  E plus (E, E);

  E zero ();

  E neg (E e);
}

```

I have a (partially implemented) annotation processor that generates tests for these properties for any class that claims to implement this interface.  

This is an example of "user" annotations: `@Commutative`, `@Associative`, etc. are implemented as part of the algebra library, not as part of the annotation processing tool; generating new properties with tests is a simple matter of adding a new annotation type with a special method that checks the property.

Annotations have been moderately well-suited to this task, although there are a number of shortcomings. For example, java annotations do not have a notion of inheritance, so my processor has to explicitly search for annotations on all superinterfaces of a class. Also, Java doesn't support marking a method with multiple copies of the same annotation, so I can't write `@DistributesOver("foo")` and `@DistributesOver("bar")` on the same method.