The easier way to implement this method is usually:

  public int read() throws IOException {
    byte[] b = new byte[1];
    int r = read(b);
    return r == 1 ? b[0] & 0xff : -1;
  }

Most callers these days do bulk IO thorugh read(byte[], int, int) and bypass the single byte read.  Thus this method is usually never used.  And JVMs these days are pretty good at cleaning up locally allocated short-term garbage like that single byte byte array so its not the end of the world that we allocate for the read.