The volatile
keyword requires that certain guarantees are satisfied when reading and writing the variable. It doesn't really make sense to talk about "removing the declaration"—no, that can't happen, because the only way that makes sense would be if the compiler ignored the declaration in your source code.
But if you are running the code in a context (e.g., single-threaded) where you couldn't tell that the runtime is actively working to meet those requirements, it is permissible for the runtime to skip that extra work.
Of your examples, the only case that might be determined at compile-time is a variable that is only written, and never read. In that case, the compiler could skip writes (if a variable is written, and no one is around to read it, does it make a sound?), but the the Java Memory Model still makes some guarantees about happens-before relationships around writing a volatile
variable, and those still have to be upheld, so it wouldn't make sense to optimize that away at compile-time.