diff --git a/src/main/java/com/alibaba/excel/metadata/Head.java b/src/main/java/com/alibaba/excel/metadata/Head.java index c578cbbc..c150fe02 100644 --- a/src/main/java/com/alibaba/excel/metadata/Head.java +++ b/src/main/java/com/alibaba/excel/metadata/Head.java @@ -3,6 +3,7 @@ package com.alibaba.excel.metadata; import java.util.ArrayList; import java.util.List; +import com.alibaba.excel.exception.ExcelGenerateException; import com.alibaba.excel.metadata.property.ColumnWidthProperty; import com.alibaba.excel.metadata.property.FontProperty; import com.alibaba.excel.metadata.property.LoopMergeProperty; @@ -64,9 +65,15 @@ public class Head { this.columnIndex = columnIndex; this.fieldName = fieldName; if (headNameList == null) { - headNameList = new ArrayList(); + this.headNameList = new ArrayList<>(); + } else { + this.headNameList = headNameList; + for (String headName : headNameList) { + if (headName == null) { + throw new ExcelGenerateException("head name can not be null."); + } + } } - this.headNameList = headNameList; this.forceIndex = forceIndex; this.forceName = forceName; } diff --git a/src/main/java/com/alibaba/excel/util/StringUtils.java b/src/main/java/com/alibaba/excel/util/StringUtils.java index 667233dc..cb6e7227 100644 --- a/src/main/java/com/alibaba/excel/util/StringUtils.java +++ b/src/main/java/com/alibaba/excel/util/StringUtils.java @@ -69,7 +69,6 @@ public class StringUtils { return true; } - /** *

Checks if a CharSequence is not empty (""), not null and not whitespace only.

* @@ -83,9 +82,9 @@ public class StringUtils { * StringUtils.isNotBlank(" bob ") = true * * - * @param cs the CharSequence to check, may be null + * @param cs the CharSequence to check, may be null * @return {@code true} if the CharSequence is - * not empty and not null and not whitespace only + * not empty and not null and not whitespace only * @since 2.0 * @since 3.0 Changed signature from isNotBlank(String) to isNotBlank(CharSequence) */ @@ -93,5 +92,97 @@ public class StringUtils { return !isBlank(cs); } + /** + *

Compares two CharSequences, returning {@code true} if they represent + * equal sequences of characters.

+ * + *

{@code null}s are handled without exceptions. Two {@code null} + * references are considered to be equal. The comparison is case sensitive.

+ * + *
+     * StringUtils.equals(null, null)   = true
+     * StringUtils.equals(null, "abc")  = false
+     * StringUtils.equals("abc", null)  = false
+     * StringUtils.equals("abc", "abc") = true
+     * StringUtils.equals("abc", "ABC") = false
+     * 
+ * + * @param cs1 the first CharSequence, may be {@code null} + * @param cs2 the second CharSequence, may be {@code null} + * @return {@code true} if the CharSequences are equal (case-sensitive), or both {@code null} + * @see Object#equals(Object) + * @since 3.0 Changed signature from equals(String, String) to equals(CharSequence, CharSequence) + */ + public static boolean equals(final CharSequence cs1, final CharSequence cs2) { + if (cs1 == cs2) { + return true; + } + if (cs1 == null || cs2 == null) { + return false; + } + if (cs1.length() != cs2.length()) { + return false; + } + if (cs1 instanceof String && cs2 instanceof String) { + return cs1.equals(cs2); + } + return regionMatches(cs1, false, 0, cs2, 0, cs1.length()); + } + + /** + * Green implementation of regionMatches. + * + * @param cs the {@code CharSequence} to be processed + * @param ignoreCase whether or not to be case insensitive + * @param thisStart the index to start on the {@code cs} CharSequence + * @param substring the {@code CharSequence} to be looked for + * @param start the index to start on the {@code substring} CharSequence + * @param length character length of the region + * @return whether the region matched + */ + public static boolean regionMatches(final CharSequence cs, final boolean ignoreCase, final int thisStart, + final CharSequence substring, final int start, final int length) { + if (cs instanceof String && substring instanceof String) { + return ((String)cs).regionMatches(ignoreCase, thisStart, (String)substring, start, length); + } + int index1 = thisStart; + int index2 = start; + int tmpLen = length; + + // Extract these first so we detect NPEs the same as the java.lang.String version + final int srcLen = cs.length() - thisStart; + final int otherLen = substring.length() - start; + + // Check for invalid parameters + if (thisStart < 0 || start < 0 || length < 0) { + return false; + } + + // Check that the regions are long enough + if (srcLen < length || otherLen < length) { + return false; + } + + while (tmpLen-- > 0) { + final char c1 = cs.charAt(index1++); + final char c2 = substring.charAt(index2++); + + if (c1 == c2) { + continue; + } + + if (!ignoreCase) { + return false; + } + + // The same check as in String.regionMatches(): + if (Character.toUpperCase(c1) != Character.toUpperCase(c2) + && Character.toLowerCase(c1) != Character.toLowerCase(c2)) { + return false; + } + } + + return true; + } } diff --git a/src/main/java/com/alibaba/excel/write/property/ExcelWriteHeadProperty.java b/src/main/java/com/alibaba/excel/write/property/ExcelWriteHeadProperty.java index dc5275f8..c2779136 100644 --- a/src/main/java/com/alibaba/excel/write/property/ExcelWriteHeadProperty.java +++ b/src/main/java/com/alibaba/excel/write/property/ExcelWriteHeadProperty.java @@ -142,7 +142,7 @@ public class ExcelWriteHeadProperty extends ExcelHeadProperty { continue; } alreadyRangeSet.add(i + "-" + j); - String headName = headNameList.get(j) == null ? "" : headNameList.get(j); + String headName = headNameList.get(j); int lastCol = i; int lastRow = j; for (int k = i + 1; k < headList.size(); k++) { diff --git a/src/test/java/com/alibaba/easyexcel/test/demo/Test1765/Data1765.xlsx b/src/test/java/com/alibaba/easyexcel/test/demo/Test1765/Data1765.xlsx deleted file mode 100644 index 3377bb76..00000000 Binary files a/src/test/java/com/alibaba/easyexcel/test/demo/Test1765/Data1765.xlsx and /dev/null differ diff --git a/src/test/java/com/alibaba/easyexcel/test/demo/Test1765/Issue1765.java b/src/test/java/com/alibaba/easyexcel/test/demo/Test1765/Issue1765.java deleted file mode 100644 index 7d9f572a..00000000 --- a/src/test/java/com/alibaba/easyexcel/test/demo/Test1765/Issue1765.java +++ /dev/null @@ -1,55 +0,0 @@ -package com.alibaba.easyexcel.test.demo.Test1765; - -import com.alibaba.easyexcel.test.util.TestFileUtil; -import com.alibaba.excel.EasyExcel; -import com.alibaba.excel.EasyExcelFactory; -import org.junit.Assert; -import org.junit.Test; - -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.InputStream; -import java.util.ArrayList; -import java.util.Date; -import java.util.List; - -public class Issue1765 { - @Test - public void test1765() throws FileNotFoundException { - String fileName = "src/test/java/com/alibaba/easyexcel/test/demo/Test1765/Data1765.xlsx"; - EasyExcel.write(fileName).head(head()).sheet("模板").doWrite(dataList()); - } - - - private List> head() { - List> list = new ArrayList>(); - List head0 = new ArrayList(); - List head1 = new ArrayList(); - List head2 = new ArrayList(); - List head3 = new ArrayList(); - head0.add("表头"); - head1.add("日期"); - head2.add(null); - head3.add("数字"); - list.add(head0); - list.add(head1); - list.add(head2); - list.add(head3); - - return list; - } - - private List> dataList() { - List> list = new ArrayList>(); - for (int i = 0; i < 5; i++) { - List data = new ArrayList(); - data.add("字符串" + i); - data.add(new Date()); - data.add(i * 2); - data.add(i * 3); - list.add(data); - } - return list; - } -}