Skip to content

Commit

Permalink
Swar 20250123 (alibaba#3310)
Browse files Browse the repository at this point in the history
* fail fast

* fail fast

* optimize parseDate

* bug fix

* check style

* ymd

* formatComplex

* optimize parseTime

* optimize lines

* optimize writeFloat
  • Loading branch information
wenshao authored Jan 23, 2025
1 parent 1e20402 commit 3cb8ff1
Show file tree
Hide file tree
Showing 8 changed files with 211 additions and 158 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ public static void fastjson2() {
long millis = System.currentTimeMillis() - start;
System.out.println("ClientsWriteUTF8Bytes-fastjson2 millis : " + millis);
// zulu8.70.0.23 :
// zulu17.40.19 : 1027
// zulu17.40.19 : 1027 970
// zulu17.40.19_vec :
// zulu17.40.19_reflect :
}
Expand Down
2 changes: 2 additions & 0 deletions core/src/main/java/com/alibaba/fastjson2/JSONReader.java
Original file line number Diff line number Diff line change
Expand Up @@ -3906,6 +3906,7 @@ public static AutoTypeBeforeHandler autoTypeFilter(boolean includeBasic, Class..

public static final class Context {
String dateFormat;
boolean formatComplex;
boolean formatyyyyMMddhhmmss19;
boolean formatyyyyMMddhhmmssT19;
boolean yyyyMMddhhmm16;
Expand Down Expand Up @@ -4240,6 +4241,7 @@ public void setDateFormat(String format) {
break;
}

this.formatComplex = !(formatyyyyMMddhhmmss19 | formatyyyyMMddhhmmssT19 | formatyyyyMMdd8 | formatISO8601);
// this.yyyyMMddhhmm16 = "yyyy-MM-dd HH:mm".equals(format);
}

Expand Down
16 changes: 2 additions & 14 deletions core/src/main/java/com/alibaba/fastjson2/JSONReaderUTF16.java
Original file line number Diff line number Diff line change
Expand Up @@ -4506,13 +4506,7 @@ public final LocalDate readLocalDate() {
final char[] chars = this.chars;
int offset = this.offset;
if (ch == '"' || ch == '\'') {
Context context = this.context;
if (context.dateFormat == null
|| context.formatyyyyMMddhhmmss19
|| context.formatyyyyMMddhhmmssT19
|| context.formatyyyyMMdd8
|| context.formatISO8601
) {
if (!context.formatComplex) {
char quote = ch;
int c10 = offset + 10;
if (c10 < chars.length
Expand Down Expand Up @@ -4576,14 +4570,8 @@ public final LocalDate readLocalDate() {
public final OffsetDateTime readOffsetDateTime() {
final char[] chars = this.chars;
final int offset = this.offset;
final Context context = this.context;
if (this.ch == '"' || this.ch == '\'') {
if (context.dateFormat == null
|| context.formatyyyyMMddhhmmss19
|| context.formatyyyyMMddhhmmssT19
|| context.formatyyyyMMdd8
|| context.formatISO8601
) {
if (!context.formatComplex) {
char quote = this.ch;
char c10;
int off21 = offset + 19;
Expand Down
66 changes: 25 additions & 41 deletions core/src/main/java/com/alibaba/fastjson2/JSONReaderUTF8.java
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@

import static com.alibaba.fastjson2.JSONFactory.*;
import static com.alibaba.fastjson2.JSONReaderJSONB.check3;
import static com.alibaba.fastjson2.util.DateUtils.*;
import static com.alibaba.fastjson2.util.IOUtils.*;
import static com.alibaba.fastjson2.util.JDKUtils.*;
import static java.lang.Long.MIN_VALUE;
Expand Down Expand Up @@ -5711,29 +5712,21 @@ public final int getStringLength() {
public final LocalDate readLocalDate() {
final byte[] bytes = this.bytes;
int offset = this.offset;
if (ch == '"' || ch == '\'') {
Context context = this.context;
if (context.dateFormat == null
|| context.formatyyyyMMddhhmmss19
|| context.formatyyyyMMddhhmmssT19
|| context.formatyyyyMMdd8
|| context.formatISO8601
) {
char quote = ch;
char quote = ch;
if (quote == '"' || quote == '\'') {
if (!this.context.formatComplex) {
int yy;
long ymd;
int c10 = offset + 10;
if (c10 < bytes.length
&& c10 < end
&& bytes[offset + 4] == '-'
&& bytes[offset + 7] == '-'
&& (yy = yy(bytes, offset)) != -1
&& ((ymd = ymd(bytes, offset + 2))) != -1L
&& bytes[offset + 10] == quote
) {
int year = IOUtils.digit4(bytes, offset);
int month = IOUtils.digit2(bytes, offset + 5);
int dom = IOUtils.digit2(bytes, offset + 8);

if ((year | month | dom) < 0) {
throw new JSONException(info("read date error"));
}
int year = yy + ((int) ymd & 0xFF);
int month = (int) (ymd >> 24) & 0xFF;
int dom = (int) (ymd >> 48) & 0xFF;

LocalDate ldt;
try {
Expand Down Expand Up @@ -5782,35 +5775,26 @@ public final LocalDate readLocalDate() {
public final OffsetDateTime readOffsetDateTime() {
final byte[] bytes = this.bytes;
final int offset = this.offset;
final Context context = this.context;
if (this.ch == '"' || this.ch == '\'') {
if (context.dateFormat == null
|| context.formatyyyyMMddhhmmss19
|| context.formatyyyyMMddhhmmssT19
|| context.formatyyyyMMdd8
|| context.formatISO8601
) {
char quote = this.ch;
char quote = this.ch;
if (quote == '"' || quote == '\'') {
if (!this.context.formatComplex) {
byte c10;
int off21 = offset + 19;
int yy;
long ymd, hms;
if (off21 < bytes.length
&& off21 < end
&& bytes[offset + 4] == '-'
&& bytes[offset + 7] == '-'
&& (yy = yy(bytes, offset)) != -1
&& ((ymd = ymd(bytes, offset + 2))) != -1L
&& ((c10 = bytes[offset + 10]) == ' ' || c10 == 'T')
&& bytes[offset + 13] == ':'
&& bytes[offset + 16] == ':'
&& ((hms = hms(bytes, offset + 11))) != -1L
) {
int year = IOUtils.digit4(bytes, offset);
int month = IOUtils.digit2(bytes, offset + 5);
int dom = IOUtils.digit2(bytes, offset + 8);
int hour = IOUtils.digit2(bytes, offset + 11);
int minute = IOUtils.digit2(bytes, offset + 14);
int second = IOUtils.digit2(bytes, offset + 17);
if ((year | month | dom | minute | second) < 0) {
ZonedDateTime zdt = readZonedDateTime();
return zdt == null ? null : zdt.toOffsetDateTime();
}
int year = yy + ((int) ymd & 0xFF);
int month = (int) (ymd >> 24) & 0xFF;
int dom = (int) (ymd >> 48) & 0xFF;
int hour = (int) hms & 0xFF;
int minute = (int) (hms >> 24) & 0xFF;
int second = (int) (hms >> 48) & 0xFF;

LocalDate localDate;
try {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1058,7 +1058,7 @@ public void writeFloat(float value) {
bytes = grow(minCapacity);
}
int i = (int) value;
if (i == value && value >= BC_INT32_NUM_MIN && value <= BC_INT32_NUM_MAX) {
if (i == value && i >= BC_INT32_NUM_MIN && i <= BC_INT32_NUM_MAX) {
putShortLE(bytes, off, (short) ((BC_FLOAT_INT & 0xFF) | (i << 8)));
off += 2;
} else {
Expand Down
114 changes: 69 additions & 45 deletions core/src/main/java/com/alibaba/fastjson2/util/DateUtils.java
Original file line number Diff line number Diff line change
Expand Up @@ -2250,41 +2250,35 @@ public static LocalDateTime parseLocalDateTime19(byte[] str, int off) {
byte c5 = str[off + 5];
byte c7 = str[off + 7];
byte c10 = str[off + 10];
byte c13 = str[off + 13];
byte c16 = str[off + 16];

int year, month, dom, hour, minute, second;
int year, month, dom;
if (((c4 == '-' && c7 == '-') || (c4 == '/' && c7 == '/'))
&& (c10 == ' ' || c10 == 'T')
&& c13 == ':' && c16 == ':'
) {
&& (c10 == ' ' || c10 == 'T')) {
year = digit4(str, off);
month = digit2(str, off + 5);
dom = digit2(str, off + 8);
hour = digit2(str, off + 11);
minute = digit2(str, off + 14);
second = digit2(str, off + 17);
} else if (c2 == '/' && c5 == '/' && (c10 == ' ' || c10 == 'T') && c13 == ':' && c16 == ':') {
} else if (c2 == '/' && c5 == '/' && (c10 == ' ' || c10 == 'T')) {
dom = digit2(str, off);
month = digit2(str, off + 3);
year = digit4(str, off + 6);
hour = digit2(str, off + 11);
minute = digit2(str, off + 14);
second = digit2(str, off + 17);
} else if (c1 == ' ' && c5 == ' ' && c10 == ' ' && c13 == ':' && c16 == ':') {
} else if (c1 == ' ' && c5 == ' ' && c10 == ' ') {
dom = digit1(str, off);
month = DateUtils.month(c2, c3, c4);
year = digit4(str, off + 6);
hour = digit2(str, off + 11);
minute = digit2(str, off + 14);
second = digit2(str, off + 17);
} else {
return null;
}

return (year | month | dom | hour | minute | second) <= 0
? null
: LocalDateTime.of(year, month, dom, hour, minute, second);
long hms = hms(str, off + 11);
if ((year | month | dom | hms) <= 0) {
return null;
}

int hour = (int) hms & 0xFF;
int minute = (int) (hms >> 24) & 0xFF;
int second = (int) (hms >> 48) & 0xFF;

return LocalDateTime.of(year, month, dom, hour, minute, second);
}

public static LocalDateTime parseLocalDateTime20(char[] str, int off) {
Expand All @@ -2311,36 +2305,36 @@ public static LocalDateTime parseLocalDateTime20(char[] str, int off) {
}

public static LocalDateTime parseLocalDateTime20(byte[] str, int off) {
long hms;
if (off + 19 > str.length
|| str[off + 2] != ' '
|| str[off + 6] != ' '
|| str[off + 11] != ' '
|| str[off + 14] != ':'
|| str[off + 17] != ':'
|| (hms = hms(str, off + 12)) == -1L
) {
return null;
}

int dom = digit2(str, off);
int month = DateUtils.month(str[off + 3], str[off + 4], str[off + 5]);
int year = digit4(str, off + 7);
int hour = digit2(str, off + 12);
int minute = digit2(str, off + 15);
int second = digit2(str, off + 18);
int hour = (int) hms & 0xFF;
int minute = (int) (hms >> 24) & 0xFF;
int second = (int) (hms >> 48) & 0xFF;

return (year | month | dom | hour | minute | second) <= 0 || hour > 24 || minute > 59 || second > 60
? null
: LocalDateTime.of(year, month, dom, hour, minute, second);
}

public static LocalDateTime parseLocalDateTime26(byte[] str, int off) {
long hms;
byte c10;
if (off + 26 > str.length
|| str[off + 4] != '-'
|| str[off + 7] != '-'
|| ((c10 = str[off + 10]) != ' ' && c10 != 'T')
|| str[off + 13] != ':'
|| str[off + 16] != ':'
|| (hms = hms(str, off + 11)) == -1L
|| str[off + 19] != '.'
) {
return null;
Expand All @@ -2349,9 +2343,9 @@ public static LocalDateTime parseLocalDateTime26(byte[] str, int off) {
int year = digit4(str, off);
int month = digit2(str, off + 5);
int dom = digit2(str, off + 8);
int hour = digit2(str, off + 11);
int minute = digit2(str, off + 14);
int second = digit2(str, off + 17);
int hour = (int) hms & 0xFF;
int minute = (int) (hms >> 24) & 0xFF;
int second = (int) (hms >> 48) & 0xFF;
int nano = readNanos(str, 6, off + 20);

return (year | month | dom | hour | minute | second | nano) <= 0 || hour > 24 || minute > 59 || second > 60
Expand Down Expand Up @@ -2386,13 +2380,13 @@ public static LocalDateTime parseLocalDateTime26(char[] str, int off) {
}

public static LocalDateTime parseLocalDateTime27(byte[] str, int off) {
long hms;
byte c10;
if (off + 27 > str.length
|| str[off + 4] != '-'
|| str[off + 7] != '-'
|| ((c10 = str[off + 10]) != ' ' && c10 != 'T')
|| str[off + 13] != ':'
|| str[off + 16] != ':'
|| (hms = hms(str, off + 11)) == -1L
|| str[off + 19] != '.'
) {
return null;
Expand All @@ -2401,9 +2395,9 @@ public static LocalDateTime parseLocalDateTime27(byte[] str, int off) {
int year = digit4(str, off);
int month = digit2(str, off + 5);
int dom = digit2(str, off + 8);
int hour = digit2(str, off + 11);
int minute = digit2(str, off + 14);
int second = digit2(str, off + 17);
int hour = (int) hms & 0xFF;
int minute = (int) (hms >> 24) & 0xFF;
int second = (int) (hms >> 48) & 0xFF;
int nano = readNanos(str, 7, off + 20);

return (year | month | dom | hour | minute | second | nano) <= 0 || hour > 24 || minute > 59 || second > 60
Expand Down Expand Up @@ -2464,13 +2458,13 @@ public static LocalDateTime parseLocalDateTime28(char[] str, int off) {
}

public static LocalDateTime parseLocalDateTime28(byte[] str, int off) {
long hms;
byte c10;
if (off + 28 > str.length
|| str[off + 4] != '-'
|| str[off + 7] != '-'
|| ((c10 = str[off + 10]) != ' ' && c10 != 'T')
|| str[off + 13] != ':'
|| str[off + 16] != ':'
|| (hms = hms(str, off + 11)) == -1L
|| str[off + 19] != '.'
) {
return null;
Expand All @@ -2479,9 +2473,9 @@ public static LocalDateTime parseLocalDateTime28(byte[] str, int off) {
int year = digit4(str, off);
int month = digit2(str, off + 5);
int dom = digit2(str, off + 8);
int hour = digit2(str, off + 11);
int minute = digit2(str, off + 14);
int second = digit2(str, off + 17);
int hour = (int) hms & 0xFF;
int minute = (int) (hms >> 24) & 0xFF;
int second = (int) (hms >> 48) & 0xFF;
int nano = readNanos(str, 8, off + 20);

return (year | month | dom | hour | minute | second | nano) <= 0 || hour > 24 || minute > 59 || second > 60
Expand All @@ -2490,13 +2484,13 @@ public static LocalDateTime parseLocalDateTime28(byte[] str, int off) {
}

public static LocalDateTime parseLocalDateTime29(byte[] str, int off) {
long hms;
byte c10;
if (off + 29 > str.length
|| str[off + 4] != '-'
|| str[off + 7] != '-'
|| ((c10 = str[off + 10]) != ' ' && c10 != 'T')
|| str[off + 13] != ':'
|| str[off + 16] != ':'
|| (hms = hms(str, off + 11)) == -1L
|| str[off + 19] != '.'
) {
return null;
Expand All @@ -2505,9 +2499,9 @@ public static LocalDateTime parseLocalDateTime29(byte[] str, int off) {
int year = digit4(str, off);
int month = digit2(str, off + 5);
int dom = digit2(str, off + 8);
int hour = digit2(str, off + 11);
int minute = digit2(str, off + 14);
int second = digit2(str, off + 17);
int hour = (int) hms & 0xFF;
int minute = (int) (hms >> 24) & 0xFF;
int second = (int) (hms >> 48) & 0xFF;
int nano = readNanos(str, 9, off + 20);

return (year | month | dom | hour | minute | second | nano) <= 0 || hour > 24 || minute > 59 || second > 60
Expand Down Expand Up @@ -9202,4 +9196,34 @@ public static int readNanos(final byte[] bytes, final int len, final int offset)
0,
0,
};

public static long hms(byte[] bytes, int off) {
long v = getLongLE(bytes, off);
long d;
if ((((v & 0xF0F0F0F0_F0F0F0F0L) - 0x30303030_30303030L) | (((d = v & 0x0F0F0F0F_0F0F0F0FL) + 0x06060006_06000606L) & 0xF0F000F0_F000F0F0L)) != 0
|| (d & 0x00000F00_000F0000L) != 0x00000a00_000a0000L) { // 00:00:00
return -1;
}
return ((d & 0x00F_0000_0F00_000FL) << 3) + ((d & 0x00F_0000_0F00_000FL) << 1) + ((d & 0xF00_000F_0000_0F00L) >> 8);
}

public static long ymd(byte[] bytes, int off) {
long v = getLongLE(bytes, off);
long d;
if (((v & 0x0000FF00_00FF0000L) != 0x00002d00_002d0000L) // yy-mm-dd
|| (((v & 0xF0F000F0_F000F0F0L) - 0x30300030_30003030L) | (((d = v & 0x0F0F000F_0F000F0FL) + 0x06060006_06000606L) & 0xF0F000F0_F000F0F0L)) != 0) {
return -1;
}
return ((d & 0x00F_0000_0F00_000FL) << 3) + ((d & 0x00F_0000_0F00_000FL) << 1) + ((d & 0xF00_000F_0000_0F00L) >> 8);
}

public static int yy(byte[] bytes, int off) {
int x = getShortLE(bytes, off);
int d;
if ((((x & 0xF0F0) - 0x3030) | (((d = x & 0x0F0F) + 0x0606) & 0xF0F0)) != 0
) {
return -1;
}
return (d & 0xF) * 1000 + (d >> 8) * 100;
}
}
Loading

0 comments on commit 3cb8ff1

Please sign in to comment.