For an adventure map, I'm building a library room with a hidden piston door that opens when you enter the correct 4-digit passcode. The passcode will be implemented by inserting books into the right slots in each of 4 separate chiseled bookshelves. To test out the concept, I built a simplified version of the circuit first in a superflat world - it only checks for a single digit being equal to 5, and turns on a redstone lamp if and only if it is.
The circuit works, but takes up a lot of space. Here is an aerial view with annotations - under the picture I'll describe what each part does in more detail.
To differentiate them from comparators, I have labeled all repeaters in the picture with "R."
The signal coming out of the back of the bookshelf when the correct book is inserted should have a value exactly equal to 5. This means testing for both the conditions (s >= 5) and (s <= 5). The first comparator only outputs a signal if the bookshelf value is >= 5. The second comparator is two blocks further away, so it checks for s <= (5 - 2).
The next step is to take both results and send them to an AND gate (circled in orange). The (s <= 5) condition, if true, turns off the inhibiting comparator while the (s >= 5) condition, if true, turns on the activating comparator. So, both conditions must be true for a signal to be sent to the lamp to turn it on.
The picture shows the result after a book has been inserted in the correct slot (#5), so the lamp is on.
An area I'm having difficulty with in particular is keeping the paths for the two conditions from intersecting too soon. To solve this, one of them goes over the other on an "overpass", but that adds a vertical space requirement for the build. The fixed-value comparisons (to signal values of 5 and 3, respectively, taking up 11 and 13 blocks) also seem inefficient.
Do you have any suggestions for how to improve this?