I think you are conflating a debug build of a program with running under the debugger (unless C# is rather strange).
Many systems - including lots of C/C++ build environments, and I expect C#, given the way Microsoft has historically designed the Visual Studio build processes - have two different types of builds you can do:
- Release build, with only info/error/warning logging, no debug symbols, extra optimizations, etc.
- Debug build, with extra logging enabled, debug symbols, possibly tuned-down optimizations.
You use debug builds while developing and debugging your program, and release builds for final QA and release. The debug builds, however, are independent of being run under a debugger - they're normal programs, and if you run them the run and still output their extra logging information. This can be very useful.
Running them under a debugger is completely orthogonal. You can run the release build under a debugger (although, lacking debug symbols, it might not be very useful). In fact, I would submit that you do not want code to change based on whether you are running under a debugger - it makes it rather difficult to debug the code being actually run in the application.
And unlike C, C++, and C#, Java has no facility for compile-time conditionals, so everything is enabled in the program. You typically deal with this by having a very fast way to check if the debugging message is to be emitted, and doing as little work as possible in the case where it is not.