skittles1412's blog

By skittles1412, history, 4 years ago, In English

Hello CodeForces,
due to the lack of a debugging template in Java (and really just any template in Java), I have decided to write my own template. To use it, add -DLOCAL to your custom VM Parameters. Note that you must use LOCAL = System.getProperty("ONLINE_JUDGE")==null; for CodeForces; this is not necessary for other OJs. Then call dbg(what you want to print) to print the "what you want to print" part to stderr.

To be more exact, when calling dbg(), It will print "Line #%d: [%s]" to stderr, where %d is the line number where you called dbg() and %s is the parameters, separated by commas. For each parameter, if it is able to be iterated using a for each loop (e.g. an array or some class implementing Iterable), it will be printed as {%s} where %s is each element printed, recursively, separated by commas. Otherwise, the .toString() method will be used.

Unfortunately, there is no way to get the names of the variables passed into the parameters of a method in Java, so I'd recommend calling dbg("variable_name", variable) to make it easier to read.

The code is not very clean (mainly due to the fact that arrays can't be cast to Iterable and because primitives can't be used in parametized methods). Please comment below if you have any suggestions or additions to the template (e.g. a class which this dbg method fails to print properly). I'll try to keep the code updated to the best of my ability.

Code

UPD:* Just realized that CodeForces doesn't allow you to query any property other than "ONLINE_JUDGE". I have accordingly updated the code and added a note.

  • Vote: I like it
  • +35
  • Vote: I do not like it

»
4 years ago, # |
  Vote: I like it +5 Vote: I do not like it

surprisingly underutilized

»
4 years ago, # |
  Vote: I like it 0 Vote: I do not like it

Auto comment: topic has been updated by skittles1412 (previous revision, new revision, compare).

»
4 years ago, # |
  Vote: I like it +5 Vote: I do not like it

Java is not my primary language, but wow, this seems like a great template! I appreciate this, given that many of the resources for debugging are written in C++.

»
4 years ago, # |
  Vote: I like it +5 Vote: I do not like it

orz

»
4 years ago, # |
  Vote: I like it 0 Vote: I do not like it

Can you like show an example or something> It would be easier to get used to this then.

  • »
    »
    4 years ago, # ^ |
      Vote: I like it 0 Vote: I do not like it

    Copy and paste this code into a java class (not including the public static class Debug) part. Then, in your main function, run dbg([insert variables]); For example,

    //This is inside your main function
    int[] arr = new int[10];
    for(int i = 0; i<10; i++) {
        arr[i] = i;
    }
    dbg(arr);
    
    • »
      »
      »
      4 years ago, # ^ |
        Vote: I like it 0 Vote: I do not like it

      Ok sounds like fun. I wont have to put print statements everywhere now. Just a little noobish question. System.getProperty("Local") is false for my local system. How should I change it for different places. You already mentioned codeforces. So i'm guessing in codeforces the variable Local will be false and dbg won't run.

      For my local system what should I do? Thanks.

      • »
        »
        »
        »
        4 years ago, # ^ |
          Vote: I like it 0 Vote: I do not like it

        For CodeForces, useboolean LOCAL = System.getProperty("ONLINE_JUDGE")==null;
        However, most OJs don't define that so run your code with -DLOCAL. To do so, google "How to add command line arguments in [insert your ide]". Follow the instructions and add -DLOCAL as a command line argument. Now, System.getProperty("LOCAL")!=null will evaluate to true.

»
4 years ago, # |
Rev. 2   Vote: I like it +5 Vote: I do not like it

This template can be made a lot simpler, take a look at my template it is just 2 lines of code. For custom classes you just need to override toString() function and you are good to go.

debug template
  • »
    »
    4 years ago, # ^ |
      Vote: I like it +6 Vote: I do not like it

    It's even better to use error stream than output stream, in case you forget to comment it, the output would still get accepted (assuming solution fits TL including extra printing to error stream). Proof

    So, the debugging template I use is

    static void dbg(Object... o){System.err.println(Arrays.deepToString(o));}
    
    • »
      »
      »
      4 years ago, # ^ |
        Vote: I like it +8 Vote: I do not like it

      There's no need to comment it. In your code, add
      static boolean LOCAL = System.getProperty("ONLINE_JUDGE")==null;
      Then change your template to
      static void dbg(Object... o){if(LOCAL)System.err.println(Arrays.deepToString(o));}

  • »
    »
    4 years ago, # ^ |
      Vote: I like it 0 Vote: I do not like it

    I realized this after about a week of writing this blog. :p

    However, having this generic template is still useful, as you can modify it however you want. Nevertheless, knowing Arrays.deepToString(); is useful for competitions where template code isn't allowed.