0

I have a big integer value which I need to convert into date time in (yyyy-mm-dd hr:ss:mss)

BigInteger sum= new BigInteger("2023062223380346");
    //  long unixSeconds = 1429582984839;
           Date date1 = new Date(sum); 
           SimpleDateFormat sdf = new SimpleDateFormat("MM/dd/yyyy h:mm:ss a"); 
           sdf.setTimeZone(TimeZone.getTimeZone("GMT+1"));
           String formattedDate = sdf.format(date1);
            System.out.println(formattedDate);

Expected output- 2023-06-22 23:38:03:466

Suyash Gupta
  • 11
  • 1
  • 5
  • its a time stamp I extracted from db table, need to format in date & time – Suyash Gupta Jul 06 '23 at 18:54
  • 2
    do you really have a `BigInteger` or is the *actual* input a `String` (as in posted code) || an standard advice - stop using classes like `Date`, `Calendar, `SimpleDateFormat`, ... outdated by classes from the `java.time` package with Java 8 (almost 10 years ago) – user16320675 Jul 06 '23 at 18:57
  • its a string, since integer can't handle such big value, I tried Big Int – Suyash Gupta Jul 06 '23 at 18:59
  • 1
    a `long` would be sufficient, **but** there is no reason to convert it into a number - converting a `String` to some date/time by using the `parse()` method (opposite of `format`) of a [`DateTimeFormatter`](https://docs.oracle.com/en/java/javase/20/docs/api/java.base/java/time/format/DateTimeFormatter.html) (the replacement for `SimpleDateFormat`) – user16320675 Jul 06 '23 at 19:02
  • I tried this LocalDateTime dateTime = LocalDateTime.parse("2023062223380346"); error- java.time.format.DateTimeParseException: Text '2023062223380346' could not be parsed at index 0 – Suyash Gupta Jul 06 '23 at 19:07
  • Your input does not match your output. Did you mean an input of `"20230622233803466"` rather than `"2023062223380346"`? (Note the last digits, one six versus two.) – Basil Bourque Jul 06 '23 at 19:18
  • This is the exact input- 2023062223380346 output format- yyyy-mm-dd hh:mm:ss – Suyash Gupta Jul 06 '23 at 19:36
  • https://stackoverflow.com/questions/36085626/localdatetime-parse-with-a-pattern-only-numbers the answer from this one works just needs to remove the `appendLiteral` and add `.appendValue(ChronoField.MILLI_OF_SECOND, 2)` and use `LocalDateTime` – Anon Jul 06 '23 at 19:45
  • @SuyashGupta In your last Comment, count the number of digits in the input. Then count the number of digits in your formatting pattern. Those two counts are *not* the same number. Can you see why that is a problem? – Basil Bourque Jul 06 '23 at 19:57
  • In your desired output, should the COLON character in `03:466` be a [decimal separator](https://en.wikipedia.org/wiki/Decimal_separator) such as COMMA `,` or FULL STOP (`.`) such as `03,466` or `03.466` ? – Basil Bourque Jul 06 '23 at 22:04

2 Answers2

1

tl;dr

LocalDateTime
.parse( 
    "20230622233803466" , 
    DateTimeFormatter.ofPattern ( "uuuuMMddHHmmssSSS" ) 
)
.toString()
.replace( "T" , " " )

2023-06-22 23:38:03.466

Details

You are using terrible legacy date-time classes were years ago supplanted by the modern java.time classes defined in JSR 310. Always use java.time classes for your date-time handling.

java.time classes

I assume your example input string "2023062223380346" is a typo, as it is missing a digit on the end when compared to your desired output 2023-06-22 23:38:03:466.

Define a formatting pattern to match your input.

String input = "20230622233803466";
DateTimeFormatter f = DateTimeFormatter.ofPattern ( "uuuuMMddHHmmssSSS" );

Parse as a LocalDateTime, a date with time of day but lacking the context of a time zone or offset-from-UTC.

LocalDateTime ldt = LocalDateTime.parse( input , f ) ;

Generate text in standard ISO 8601 format.

String iso8601 = ldt.toString() ; 

Replace the T in the middle with a SPACE, per your desired output.

String output = iso8601.replace( "T" , " " ) ;

See this code run at Ideone.com.

iso8601 = 2023-06-22T23:38:03.466

output = 2023-06-22 23:38:03.466

Apparently you want to interpret this as representing a moment in a specific time zone. Use time zone names rather than assuming an offset. Offsets can vary for different periods of time — that is the definition of a time zone, a named history of the past, present, and future changes to the offset used by the people of a particular region as decided by their politicians.

ZoneId z = ZoneId.of( "Europe/London" ) ;
ZonedDateTime zdt = ldt.atZone( z ) ;

zdt.toString() = 2023-06-22T23:38:03.466+01:00[Europe/London]


Tip: Educate the publisher of your data about the benefits of using standard ISO 8601 formats when communicating date-time values textually.

Basil Bourque
  • 303,325
  • 100
  • 852
  • 1,154
  • @user16320675 I posted a Comment to ask if that is a typo. This Question is really such a mess that I regret posting an Answer at all. The Question should have been closed for its poor quality. – Basil Bourque Jul 06 '23 at 22:06
0

In case you get a strign with known format, you can extract required part and build any date/time object, that accept all these parts separately. E.g. ZonedDateTime.

In case you nee a Date object, you can build it based on ZonedDateTime.

public static void main(String... args) {
    String str = "2023062223380346";
    ZonedDateTime zonedDateTime = convert(str, ZoneId.of("Europe/London"));
    System.out.println(zonedDateTime);  // 2023-06-22T23:38:03.000000046+01:00[Europe/London]
}

public static ZonedDateTime convert(String str, ZoneId zoneId) {
    return ZonedDateTime.of(Integer.parseInt(str.substring(0, 4)),
                            Integer.parseInt(str.substring(4, 6)),
                            Integer.parseInt(str.substring(6, 8)),
                            Integer.parseInt(str.substring(8, 10)),
                            Integer.parseInt(str.substring(10, 12)),
                            Integer.parseInt(str.substring(12, 14)),
                            Integer.parseInt(str.substring(14)),
                            zoneId);
}
Oleg Cherednik
  • 17,377
  • 4
  • 21
  • 35