Merge branch 'eugenp:master' into master

This commit is contained in:
JoannaaKL 2022-03-14 21:02:32 +01:00 committed by GitHub
commit 837cf3194a
719 changed files with 19190 additions and 2266 deletions

BIN
.local-db/todos.mv.db Normal file

Binary file not shown.

BIN
.local-db/topics.mv.db Normal file

Binary file not shown.

View File

@ -1,7 +1,5 @@
package com.baeldung.algorithms.dfs;
import java.util.LinkedList;
import java.util.Queue;
import java.util.Stack;
public class BinaryTree {
@ -124,69 +122,43 @@ public class BinaryTree {
}
}
public void traverseLevelOrder() {
if (root == null) {
return;
}
Queue<Node> nodes = new LinkedList<>();
nodes.add(root);
while (!nodes.isEmpty()) {
Node node = nodes.remove();
System.out.print(" " + node.value);
if (node.left != null) {
nodes.add(node.left);
}
if (node.left != null) {
nodes.add(node.right);
}
}
}
public void traverseInOrderWithoutRecursion() {
Stack<Node> stack = new Stack<Node>();
Stack<Node> stack = new Stack<>();
Node current = root;
stack.push(root);
while(! stack.isEmpty()) {
while(current.left != null) {
current = current.left;
stack.push(current);
}
current = stack.pop();
visit(current.value);
if(current.right != null) {
current = current.right;
while (current != null || !stack.isEmpty()) {
while (current != null) {
stack.push(current);
current = current.left;
}
Node top = stack.pop();
visit(top.value);
current = top.right;
}
}
public void traversePreOrderWithoutRecursion() {
Stack<Node> stack = new Stack<Node>();
Node current = root;
Stack<Node> stack = new Stack<>();
Node current;
stack.push(root);
while(! stack.isEmpty()) {
current = stack.pop();
visit(current.value);
if(current.right != null)
stack.push(current.right);
if(current.left != null)
stack.push(current.left);
}
}
}
public void traversePostOrderWithoutRecursion() {
Stack<Node> stack = new Stack<Node>();
Stack<Node> stack = new Stack<>();
Node prev = root;
Node current = root;
Node current;
stack.push(root);
while (!stack.isEmpty()) {
@ -206,14 +178,14 @@ public class BinaryTree {
stack.push(current.left);
}
}
}
}
private void visit(int value) {
System.out.print(" " + value);
}
}
class Node {
private void visit(int value) {
System.out.print(" " + value);
}
static class Node {
int value;
Node left;
Node right;

View File

@ -1,11 +1,11 @@
package com.baeldung.algorithms.dfs;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
import org.junit.Test;
public class BinaryTreeUnitTest {
@Test
@ -13,7 +13,7 @@ public class BinaryTreeUnitTest {
BinaryTree bt = createBinaryTree();
assertTrue(!bt.isEmpty());
assertFalse(bt.isEmpty());
}
@Test
@ -111,14 +111,6 @@ public class BinaryTreeUnitTest {
bt.traversePostOrderWithoutRecursion();
}
@Test
public void givenABinaryTree_WhenTraversingLevelOrder_ThenPrintValues() {
BinaryTree bt = createBinaryTree();
bt.traverseLevelOrder();
}
private BinaryTree createBinaryTree() {
BinaryTree bt = new BinaryTree();

View File

@ -27,3 +27,4 @@ HELP.md
### VS Code ###
.vscode/

View File

@ -4,15 +4,15 @@ This following table contains test URLs that can be used with the Olingo V2 demo
| URL | Description |
|------------------------------------------|-------------------------------------------------|
| `http://localhost:8180/odata/$metadata` | fetch OData metadata document |
| `http://localhost:8180/odata/CarMakers?$top=10&$skip=10` | Get 10 entities starting at offset 10 |
| `http://localhost:8180/odata/CarMakers?$count` | Return total count of entities in this set |
| `http://localhost:8180/odata/CarMakers?$filter=startswith(Name,'B')` | Return entities where the *Name* property starts with 'B' |
| `http://localhost:8180/odata/CarModels?$filter=Year eq 2008 and CarMakerDetails/Name eq 'BWM'` | Return *CarModel* entities where the *Name* property of its maker starts with 'B' |
| `http://localhost:8180/odata/CarModels(1L)?$expand=CarMakerDetails` | Return the *CarModel* with primary key '1', along with its maker|
| `http://localhost:8180/odata/CarModels(1L)?$select=Name,Sku` | Return the *CarModel* with primary key '1', returing only its *Name* and *Sku* properties |
| `http://localhost:8180/odata/CarModels?$orderBy=Name asc,Sku desc` | Return *CarModel* entities, ordered by the their *Name* and *Sku* properties |
| `http://localhost:8180/odata/CarModels?$format=json` | Return *CarModel* entities, using a JSON representation|
| `http://localhost:8080/odata/$metadata` | fetch OData metadata document |
| `http://localhost:8080/odata/CarMakers?$top=10&$skip=10` | Get 10 entities starting at offset 10 |
| `http://localhost:8080/odata/CarMakers?$count` | Return total count of entities in this set |
| `http://localhost:8080/odata/CarMakers?$filter=startswith(Name,'B')` | Return entities where the *Name* property starts with 'B' |
| `http://localhost:8080/odata/CarModels?$filter=Year eq 2008 and CarMakerDetails/Name eq 'BWM'` | Return *CarModel* entities where the *Name* property of its maker starts with 'B' |
| `http://localhost:8080/odata/CarModels(1L)?$expand=CarMakerDetails` | Return the *CarModel* with primary key '1', along with its maker|
| `http://localhost:8080/odata/CarModels(1L)?$select=Name,Sku` | Return the *CarModel* with primary key '1', returing only its *Name* and *Sku* properties |
| `http://localhost:8080/odata/CarModels?$orderBy=Name asc,Sku desc` | Return *CarModel* entities, ordered by the their *Name* and *Sku* properties |
| `http://localhost:8080/odata/CarModels?$format=json` | Return *CarModel* entities, using a JSON representation|

View File

@ -3,16 +3,16 @@
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.baeldung.examples.olingo2</groupId>
<artifactId>olingo2</artifactId>
<name>olingo2</name>
<description>Sample Olingo 2 Project</description>
<groupId>com.baeldung.examples.olingo</groupId>
<artifactId>apache-olingo</artifactId>
<name>apache-olingo</name>
<description>Sample Apache Olingo Project</description>
<parent>
<groupId>com.baeldung</groupId>
<artifactId>parent-boot-2</artifactId>
<version>0.0.1-SNAPSHOT</version>
<relativePath>../../parent-boot-2</relativePath>
<relativePath>../parent-boot-2</relativePath>
</parent>
<dependencies>
@ -43,7 +43,7 @@
<dependency>
<groupId>org.apache.olingo</groupId>
<artifactId>olingo-odata2-core</artifactId>
<version>${olingo2.version}</version>
<version>${olingo.version}</version>
<!-- Avoid jax-rs version conflict by excluding Olingo's version -->
<exclusions>
<exclusion>
@ -55,12 +55,12 @@
<dependency>
<groupId>org.apache.olingo</groupId>
<artifactId>olingo-odata2-jpa-processor-core</artifactId>
<version>${olingo2.version}</version>
<version>${olingo.version}</version>
</dependency>
<dependency>
<groupId>org.apache.olingo</groupId>
<artifactId>olingo-odata2-jpa-processor-ref</artifactId>
<version>${olingo2.version}</version>
<version>${olingo.version}</version>
<exclusions>
<exclusion>
<groupId>org.eclipse.persistence</groupId>
@ -80,7 +80,7 @@
</build>
<properties>
<olingo2.version>2.0.11</olingo2.version>
<olingo.version>2.0.11</olingo.version>
</properties>
</project>

View File

@ -27,11 +27,6 @@ import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;
/**
* ODataJPAServiceFactory implementation for our sample domain
* @author Philippe
*
*/
@Component
public class CarsODataJPAServiceFactory extends ODataJPAServiceFactory {
@ -44,7 +39,7 @@ public class CarsODataJPAServiceFactory extends ODataJPAServiceFactory {
/**
* This method will be called by Olingo on every request to
* initialize the ODataJPAContext that will be used.
* initialize the ODataJPAContext that will be used.
*/
@Override
public ODataJPAContext initializeODataJPAContext() throws ODataJPARuntimeException {
@ -54,14 +49,14 @@ public class CarsODataJPAServiceFactory extends ODataJPAServiceFactory {
ODataContext octx = ctx.getODataContext();
HttpServletRequest request = (HttpServletRequest)octx.getParameter(ODataContext.HTTP_SERVLET_REQUEST_OBJECT);
EntityManager em = (EntityManager)request.getAttribute(JerseyConfig.EntityManagerFilter.EM_REQUEST_ATTRIBUTE);
// Here we're passing the EM that was created by the EntityManagerFilter (see JerseyConfig)
ctx.setEntityManager(new EntityManagerWrapper(em));
ctx.setPersistenceUnitName("default");
// We're managing the EM's lifecycle, so we must inform Olingo that it should not
// try to manage transactions and/or persistence sessions
ctx.setContainerManaged(true);
ctx.setContainerManaged(true);
return ctx;
}

View File

@ -1,6 +1,12 @@
package com.baeldung.examples.olingo2;
package com.baeldung.examples.olingo2;
import java.io.IOException;
import org.apache.olingo.odata2.api.ODataServiceFactory;
import org.apache.olingo.odata2.core.rest.ODataRootLocator;
import org.apache.olingo.odata2.core.rest.app.ODataApplication;
import org.glassfish.jersey.server.ResourceConfig;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
@ -15,28 +21,15 @@ import javax.ws.rs.container.ContainerResponseFilter;
import javax.ws.rs.core.Context;
import javax.ws.rs.ext.Provider;
import org.apache.olingo.odata2.api.ODataServiceFactory;
import org.apache.olingo.odata2.core.rest.ODataRootLocator;
import org.apache.olingo.odata2.core.rest.app.ODataApplication;
import org.glassfish.jersey.server.ResourceConfig;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;
/**
* Jersey JAX-RS configuration
* @author Philippe
*
*/
@Component
@ApplicationPath("/odata")
public class JerseyConfig extends ResourceConfig {
public JerseyConfig(CarsODataJPAServiceFactory serviceFactory, EntityManagerFactory emf) {
public JerseyConfig(CarsODataJPAServiceFactory serviceFactory, EntityManagerFactory emf) {
ODataApplication app = new ODataApplication();
app
.getClasses()
.forEach( c -> {
@ -46,11 +39,11 @@ public class JerseyConfig extends ResourceConfig {
register(c);
}
});
register(new CarsRootLocator(serviceFactory));
register(new CarsRootLocator(serviceFactory));
register( new EntityManagerFilter(emf));
}
/**
* This filter handles the EntityManager transaction lifecycle.
* @author Philippe
@ -72,7 +65,7 @@ public class JerseyConfig extends ResourceConfig {
}
@Override
public void filter(ContainerRequestContext ctx) throws IOException {
public void filter(ContainerRequestContext ctx) {
log.info("[I60] >>> filter");
EntityManager em = this.emf.createEntityManager();
httpRequest.setAttribute(EM_REQUEST_ATTRIBUTE, em);
@ -85,7 +78,7 @@ public class JerseyConfig extends ResourceConfig {
}
@Override
public void filter(ContainerRequestContext requestContext, ContainerResponseContext responseContext) throws IOException {
public void filter(ContainerRequestContext requestContext, ContainerResponseContext responseContext) {
log.info("[I68] <<< filter");
EntityManager em = (EntityManager) httpRequest.getAttribute(EM_REQUEST_ATTRIBUTE);

View File

@ -7,7 +7,7 @@ import org.springframework.boot.web.servlet.support.SpringBootServletInitializer
@SpringBootApplication
public class Olingo2SampleApplication extends SpringBootServletInitializer {
public static void main(String[] args) {
public static void main(String[] args) {
SpringApplication.run(Olingo2SampleApplication.class);
}
}

View File

@ -7,7 +7,7 @@ import org.springframework.test.context.junit4.SpringRunner;
@RunWith(SpringRunner.class)
@SpringBootTest
public class Olingo2SampleApplicationUnitTest {
public class Olingo2SampleApplicationIntegrationTest {
@Test
public void contextLoads() {

View File

@ -9,4 +9,6 @@ This module contains articles about Apache POI.
- [Numeric Format Using POI](https://www.baeldung.com/apache-poi-numeric-format)
- [Microsoft Word Processing in Java with Apache POI](https://www.baeldung.com/java-microsoft-word-with-apache-poi)
- [Creating a MS PowerPoint Presentation in Java](https://www.baeldung.com/apache-poi-slideshow)
- [Finding the Last Row in an Excel Spreadsheet From Java](https://www.baeldung.com/java-excel-find-last-row)
- [Setting Formulas in Excel with Apache POI](https://www.baeldung.com/java-apache-poi-set-formulas)
- More articles: [[<-- prev]](../apache-poi)

View File

@ -22,7 +22,7 @@
</dependencies>
<properties>
<poi.version>5.0.0</poi.version>
<poi.version>5.2.0</poi.version>
</properties>
</project>

View File

@ -1,26 +1,25 @@
package com.baeldung.poi.excel.setformula;
import org.apache.poi.xssf.usermodel.XSSFCell;
import org.apache.poi.xssf.usermodel.XSSFFormulaEvaluator;
import org.apache.poi.xssf.usermodel.XSSFSheet;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
public class ExcelFormula {
public double setFormula(String fileLocation, XSSFWorkbook wb, String formula) throws IOException {
XSSFSheet sheet = wb.getSheetAt(0);
int lastCellNum = sheet.getRow(0).getLastCellNum();
XSSFCell formulaCell = sheet.getRow(0).createCell(lastCellNum);
formulaCell.setCellFormula(formula);
XSSFFormulaEvaluator formulaEvaluator = wb.getCreationHelper().createFormulaEvaluator();
formulaEvaluator.evaluateFormulaCell(formulaCell);
FileOutputStream fileOut = new FileOutputStream(new File(fileLocation));
wb.write(fileOut);
wb.close();
fileOut.close();
return formulaCell.getNumericCellValue();
}
}
package com.baeldung.poi.excel.setformula;
import org.apache.poi.xssf.usermodel.XSSFCell;
import org.apache.poi.xssf.usermodel.XSSFFormulaEvaluator;
import org.apache.poi.xssf.usermodel.XSSFSheet;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import java.io.FileOutputStream;
import java.io.IOException;
public class ExcelFormula {
public double setFormula(String fileLocation, XSSFWorkbook wb, String formula) throws IOException {
XSSFSheet sheet = wb.getSheetAt(0);
int lastCellNum = sheet.getRow(0).getLastCellNum();
XSSFCell formulaCell = sheet.getRow(0).createCell(lastCellNum);
formulaCell.setCellFormula(formula);
XSSFFormulaEvaluator formulaEvaluator = wb.getCreationHelper().createFormulaEvaluator();
formulaEvaluator.evaluateFormulaCell(formulaCell);
FileOutputStream fileOut = new FileOutputStream(fileLocation);
wb.write(fileOut);
wb.close();
fileOut.close();
return formulaCell.getNumericCellValue();
}
}

View File

@ -0,0 +1,67 @@
package com.baeldung.poi.excel.lastrow;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.junit.Before;
import org.junit.Test;
import java.io.IOException;
import java.net.URISyntaxException;
import java.nio.file.Paths;
import static org.junit.jupiter.api.Assertions.*;
public class LastRowUnitTest {
private static final String FILE_NAME = "lastRowTest.xlsx";
private String fileLocation;
@Before
public void setup() throws URISyntaxException {
fileLocation = Paths.get(ClassLoader.getSystemResource(FILE_NAME).toURI()).toString();
}
@Test
public void givenExampleGrid_whenGetRow_thenReturnRowObjectIfModified() throws IOException {
Workbook workbook = new XSSFWorkbook(fileLocation);
Sheet sheet = workbook.getSheetAt(0);
assertEquals(7, sheet.getLastRowNum());
assertEquals(6, sheet.getPhysicalNumberOfRows());
assertNotNull(sheet.getRow(0));
assertNotNull(sheet.getRow(1));
assertNotNull(sheet.getRow(2));
assertNotNull(sheet.getRow(3));
assertNull(sheet.getRow(4));
assertNull(sheet.getRow(5));
assertNotNull(sheet.getRow(6));
assertNotNull(sheet.getRow(7));
assertNull(sheet.getRow(8));
assertSame(sheet.getRow(7), getLastRowFromSheet(sheet));
}
@Test
public void givenEmptySheet_whenGetRow_thenReturnNull() throws IOException {
Workbook workbook = new XSSFWorkbook(fileLocation);
Sheet sheet = workbook.getSheetAt(1);
assertEquals(-1, sheet.getLastRowNum());
assertEquals(0, sheet.getPhysicalNumberOfRows());
assertNull(sheet.getRow(0));
assertSame(sheet.getRow(0), getLastRowFromSheet(sheet));
}
public static Row getLastRowFromSheet(Sheet sheet) {
Row lastRow = null;
int lastRowNum = sheet.getLastRowNum();
if (lastRowNum >= 0) {
lastRow = sheet.getRow(lastRowNum);
}
return lastRow;
}
}

View File

@ -3,18 +3,19 @@ package com.baeldung.poi.excel.setformula;
import org.apache.poi.ss.util.CellReference;
import org.apache.poi.xssf.usermodel.XSSFSheet;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.junit.Assert;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.net.URISyntaxException;
import java.nio.file.Paths;
import static org.junit.jupiter.api.Assertions.assertEquals;
class ExcelFormulaUnitTest {
private static String FILE_NAME = "com/baeldung/poi/excel/setformula/SetFormulaTest.xlsx";
private static final String FILE_NAME = "com/baeldung/poi/excel/setformula/SetFormulaTest.xlsx";
private String fileLocation;
private ExcelFormula excelFormula;
@ -26,7 +27,7 @@ class ExcelFormulaUnitTest {
@Test
void givenExcelData_whenSetFormula_thenSuccess() throws IOException {
FileInputStream inputStream = new FileInputStream(new File(fileLocation));
FileInputStream inputStream = new FileInputStream(fileLocation);
XSSFWorkbook wb = new XSSFWorkbook(inputStream);
XSSFSheet sheet = wb.getSheetAt(0);
double resultColumnA = 0;
@ -46,6 +47,6 @@ class ExcelFormulaUnitTest {
double resultValue = excelFormula.setFormula(fileLocation, wb, sumFormulaForColumnA + "-" + sumFormulaForColumnB);
Assert.assertEquals(resultColumnA - resultColumnB, resultValue, 0d);
assertEquals(resultColumnA - resultColumnB, resultValue, 0d);
}
}

Binary file not shown.

View File

@ -1,3 +1,5 @@
*.docx
temp.xls
temp.xlsx
CellStyleTest_output.xlsx

View File

@ -8,10 +8,10 @@ This module contains articles about Apache POI.
- [Merge Cells in Excel Using Apache POI](https://www.baeldung.com/java-apache-poi-merge-cells)
- [Get String Value of Excel Cell with Apache POI](https://www.baeldung.com/java-apache-poi-cell-string-value)
- [Read Excel Cell Value Rather Than Formula With Apache POI](https://www.baeldung.com/apache-poi-read-cell-value-formula)
- [Setting Formulas in Excel with Apache POI](https://www.baeldung.com/java-apache-poi-set-formulas)
- [Insert a Row in Excel Using Apache POI](https://www.baeldung.com/apache-poi-insert-excel-row)
- [Multiline Text in Excel Cell Using Apache POI](https://www.baeldung.com/apache-poi-write-multiline-text)
- [Set Background Color of a Cell with Apache POI](https://www.baeldung.com/apache-poi-background-color)
- [Add Borders to Excel Cells With Apache POI](https://www.baeldung.com/apache-poi-add-borders)
- [Reading Values From Excel in Java](https://www.baeldung.com/java-read-dates-excel)
- [Change Cell Font Style with Apache POI](https://www.baeldung.com/apache-poi-change-cell-font)
- More articles: [[next -->]](../apache-poi-2)

View File

@ -32,9 +32,27 @@
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-resources-plugin</artifactId>
<version>${maven.resources.plugin.version}</version>
<configuration>
<encoding>UTF-8</encoding>
<nonFilteredFileExtensions>
<nonFilteredFileExtension>xlsx</nonFilteredFileExtension>
<nonFilteredFileExtension>xls</nonFilteredFileExtension>
</nonFilteredFileExtensions>
</configuration>
</plugin>
</plugins>
</build>
<properties>
<poi.version>4.1.1</poi.version>
<poi.version>5.2.0</poi.version>
<jexcel.version>1.0.6</jexcel.version>
<maven.resources.plugin.version>3.2.0</maven.resources.plugin.version>
</properties>
</project>

View File

@ -1,25 +1,24 @@
package com.baeldung.poi.excel;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.CellType;
import org.apache.poi.ss.usermodel.CellStyle;
import org.apache.poi.ss.usermodel.DateUtil;
import org.apache.poi.ss.usermodel.FillPatternType;
import org.apache.poi.ss.usermodel.IndexedColors;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.apache.poi.xssf.usermodel.XSSFFont;
import org.apache.poi.ss.usermodel.DateUtil;
import org.apache.poi.ss.usermodel.FillPatternType;
import java.io.File;
import java.io.FileOutputStream;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.Map;
import java.util.HashMap;
import java.util.ArrayList;
import java.util.List;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
public class ExcelPOIHelper {
@ -33,7 +32,7 @@ public class ExcelPOIHelper {
for (Row row : sheet) {
data.put(i, new ArrayList<String>());
for (Cell cell : row) {
switch (cell.getCellTypeEnum()) {
switch (cell.getCellType()) {
case STRING:
data.get(i)
.add(cell.getRichStringCellValue()

View File

@ -44,6 +44,7 @@ public class ExcelUtility {
}
}
inputStream.close();
baeuldungWorkBook.close();
} catch (IOException e) {
throw e;

View File

@ -1,128 +0,0 @@
package com.baeldung.poi.excel;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.CellType;
import org.apache.poi.ss.usermodel.DateUtil;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
public class ExcelUtility {
<<<<<<< HEAD
private static final String ENDLINE = System.getProperty("line.separator");
public static String readExcel(String filePath) throws IOException {
File file = new File(filePath);
FileInputStream inputStream = null;
StringBuilder toReturn = new StringBuilder();
try {
inputStream = new FileInputStream(file);
Workbook baeuldungWorkBook = new XSSFWorkbook(inputStream);
for (Sheet sheet : baeuldungWorkBook) {
toReturn.append("--------------------------------------------------------------------")
.append(ENDLINE);
toReturn.append("Worksheet :")
.append(sheet.getSheetName())
.append(ENDLINE);
toReturn.append("--------------------------------------------------------------------")
.append(ENDLINE);
int firstRow = sheet.getFirstRowNum();
int lastRow = sheet.getLastRowNum();
for (int index = firstRow + 1; index <= lastRow; index++) {
Row row = sheet.getRow(index);
toReturn.append("|| ");
for (int cellIndex = row.getFirstCellNum(); cellIndex < row.getLastCellNum(); cellIndex++) {
Cell cell = row.getCell(cellIndex, Row.MissingCellPolicy.CREATE_NULL_AS_BLANK);
printCellValue(cell, toReturn);
}
toReturn.append(" ||")
.append(ENDLINE);
}
}
inputStream.close();
} catch (IOException e) {
throw e;
}
return toReturn.toString();
}
public static void printCellValue(Cell cell, StringBuilder toReturn) {
CellType cellType = cell.getCellType()
.equals(CellType.FORMULA) ? cell.getCachedFormulaResultType() : cell.getCellType();
if (cellType.equals(CellType.STRING)) {
toReturn.append(cell.getStringCellValue())
.append(" | ");
}
if (cellType.equals(CellType.NUMERIC)) {
if (DateUtil.isCellDateFormatted(cell)) {
toReturn.append(cell.getDateCellValue())
.append(" | ");
} else {
toReturn.append(cell.getNumericCellValue())
.append(" | ");
}
}
if (cellType.equals(CellType.BOOLEAN)) {
toReturn.append(cell.getBooleanCellValue())
.append(" | ");
}
}
=======
private static final String ENDLINE = System.getProperty("line.separator");
public static String readExcel(String filePath) throws IOException {
File file = new File(filePath);
FileInputStream inputStream = null;
StringBuilder toReturn = new StringBuilder();
try {
inputStream = new FileInputStream(file);
Workbook baeuldungWorkBook = new XSSFWorkbook(inputStream);
for (Sheet sheet : baeuldungWorkBook) {
toReturn.append("--------------------------------------------------------------------").append(ENDLINE);
toReturn.append("Worksheet :").append(sheet.getSheetName()).append(ENDLINE);
toReturn.append("--------------------------------------------------------------------").append(ENDLINE);
int firstRow = sheet.getFirstRowNum();
int lastRow = sheet.getLastRowNum();
for (int index = firstRow + 1; index <= lastRow; index++) {
Row row = sheet.getRow(index);
toReturn.append("|| ");
for (int cellIndex = row.getFirstCellNum(); cellIndex < row.getLastCellNum(); cellIndex++) {
Cell cell = row.getCell(cellIndex, Row.MissingCellPolicy.CREATE_NULL_AS_BLANK);
printCellValue(cell, toReturn);
}
toReturn.append(" ||").append(ENDLINE);
}
}
inputStream.close();
} catch (IOException e) {
throw e;
}
return toReturn.toString();
}
public static void printCellValue(Cell cell, StringBuilder toReturn) {
CellType cellType = cell.getCellType().equals(CellType.FORMULA) ? cell.getCachedFormulaResultType()
: cell.getCellType();
if (cellType.equals(CellType.STRING)) {
toReturn.append(cell.getStringCellValue()).append(" | ");
}
if (cellType.equals(CellType.NUMERIC)) {
if (DateUtil.isCellDateFormatted(cell)) {
toReturn.append(cell.getDateCellValue()).append(" | ");
} else {
toReturn.append(cell.getNumericCellValue()).append(" | ");
}
}
if (cellType.equals(CellType.BOOLEAN)) {
toReturn.append(cell.getBooleanCellValue()).append(" | ");
}
}
>>>>>>> master
}

View File

@ -0,0 +1,25 @@
package com.baeldung.poi.excel.cellstyle;
import org.apache.poi.hssf.util.HSSFColor.HSSFColorPredefined;
import org.apache.poi.ss.usermodel.CellStyle;
import org.apache.poi.ss.usermodel.Font;
import org.apache.poi.ss.usermodel.HorizontalAlignment;
import org.apache.poi.ss.usermodel.VerticalAlignment;
import org.apache.poi.ss.usermodel.Workbook;
public class CellStyler {
public CellStyle createWarningColor(Workbook workbook) {
CellStyle style = workbook.createCellStyle();
Font font = workbook.createFont();
font.setFontName("Courier New");
font.setBold(true);
font.setUnderline(Font.U_SINGLE);
font.setColor(HSSFColorPredefined.DARK_RED.getIndex());
style.setFont(font);
style.setAlignment(HorizontalAlignment.CENTER);
style.setVerticalAlignment(VerticalAlignment.CENTER);
return style;
}
}

View File

@ -1,25 +1,18 @@
package com.baeldung.jexcel;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import jxl.read.biff.BiffException;
import java.util.Map;
import java.util.ArrayList;
import java.util.List;
import com.baeldung.jexcel.JExcelHelper;
import jxl.write.WriteException;
import jxl.read.biff.BiffException;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
import org.junit.Test;
import org.junit.Before;
import java.io.File;
import java.io.IOException;
import java.util.List;
import java.util.Map;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import jxl.read.biff.BiffException;
import jxl.write.WriteException;
public class JExcelIntegrationTest {

View File

@ -1,22 +1,15 @@
package com.baeldung.poi.excel;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import jxl.read.biff.BiffException;
import java.util.Map;
import java.util.ArrayList;
import java.util.List;
import com.baeldung.poi.excel.ExcelPOIHelper;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
import org.junit.Test;
import org.junit.Before;
import java.io.File;
import java.io.IOException;
import java.util.List;
import java.util.Map;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
public class ExcelIntegrationTest {

View File

@ -1,112 +0,0 @@
package com.baeldung.poi.excel;
import static org.junit.Assert.assertEquals;
import static org.junit.jupiter.api.Assertions.assertThrows;
import java.io.IOException;
import java.net.URISyntaxException;
import java.nio.file.Paths;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import org.junit.Before;
import org.junit.Test;
public class ExcelUtilityUnitTest {
<<<<<<< HEAD
private static final String FILE_NAME = "baeldung.xlsx";
private String fileLocation;
private static final String ENDLINE = System.getProperty("line.separator");
private StringBuilder output;
@Before
public void setupUnitTest() throws IOException, URISyntaxException, ParseException {
output = new StringBuilder();
output.append("--------------------------------------------------------------------")
.append(ENDLINE);
output.append("Worksheet :Sheet1")
.append(ENDLINE);
output.append("--------------------------------------------------------------------")
.append(ENDLINE);
output.append("|| Name1 | Surname1 | 3.55696564113E11 | ")
.append(new SimpleDateFormat("dd/MM/yyyy").parse("4/11/2021")
.toString())
.append(" | ‡ | ||")
.append(ENDLINE);
output.append("|| Name2 | Surname2 | 5.646513512E9 | ")
.append(new SimpleDateFormat("dd/MM/yyyy").parse("4/12/2021")
.toString())
.append(" | false | ||")
.append(ENDLINE);
output.append("|| Name3 | Surname3 | 3.55696564113E11 | ")
.append(new SimpleDateFormat("dd/MM/yyyy").parse("4/11/2021")
.toString())
.append(" | 7.17039641738E11 | ||")
.append(ENDLINE);
output.append("--------------------------------------------------------------------")
.append(ENDLINE);
output.append("Worksheet :Sheet2")
.append(ENDLINE);
output.append("--------------------------------------------------------------------")
.append(ENDLINE);
output.append("|| Name4 | Surname4 | 3.55675623232E11 | 13/04/2021 | ||")
.append(ENDLINE);
fileLocation = Paths.get(ClassLoader.getSystemResource(FILE_NAME)
.toURI())
.toString();
}
@Test
public void givenStringPath_whenReadExcel_thenReturnStringValue() throws IOException {
assertEquals(output.toString(), ExcelUtility.readExcel(fileLocation));
}
@Test
public void givenStringPath_whenReadExcel_thenThrowException() {
assertThrows(IOException.class, () -> {
ExcelUtility.readExcel("baeldung");
});
}
=======
private static final String FILE_NAME = "baeldung.xlsx";
private String fileLocation;
private static final String ENDLINE = System.getProperty("line.separator");
private StringBuilder output;
@Before
public void setupUnitTest() throws IOException, URISyntaxException, ParseException {
output = new StringBuilder();
output.append("--------------------------------------------------------------------").append(ENDLINE);
output.append("Worksheet :Sheet1").append(ENDLINE);
output.append("--------------------------------------------------------------------").append(ENDLINE);
output.append("|| Name1 | Surname1 | 3.55696564113E11 | ").append(new SimpleDateFormat("dd/MM/yyyy").parse("4/11/2021").toString()).append(" | ‡ | ||")
.append(ENDLINE);
output.append("|| Name2 | Surname2 | 5.646513512E9 | ").append(new SimpleDateFormat("dd/MM/yyyy").parse("4/12/2021").toString()).append(" | false | ||")
.append(ENDLINE);
output.append("|| Name3 | Surname3 | 3.55696564113E11 | ").append(new SimpleDateFormat("dd/MM/yyyy").parse("4/11/2021").toString()).append(" | 7.17039641738E11 | ||")
.append(ENDLINE);
output.append("--------------------------------------------------------------------").append(ENDLINE);
output.append("Worksheet :Sheet2").append(ENDLINE);
output.append("--------------------------------------------------------------------").append(ENDLINE);
output.append("|| Name4 | Surname4 | 3.55675623232E11 | 13/04/2021 | ||").append(ENDLINE);
fileLocation = Paths.get(ClassLoader.getSystemResource(FILE_NAME).toURI()).toString();
}
@Test
public void givenStringPath_whenReadExcel_thenReturnStringValue() throws IOException {
assertEquals(output.toString(), ExcelUtility.readExcel(fileLocation));
}
@Test
public void givenStringPath_whenReadExcel_thenThrowException() {
assertThrows(IOException.class, () -> {
ExcelUtility.readExcel("baeldung");
});
}
>>>>>>> master
}

View File

@ -12,7 +12,7 @@ import java.nio.file.Paths;
import static org.junit.Assert.assertEquals;
public class CellBorderHandlerUnitTest {
private static final String FILE_NAME = "cellstyle/CellStyleHandlerTest.xlsx";
private static final String FILE_NAME = "cellstyle/CellStyleBorderHandlerTest.xlsx";
private static final int SHEET_INDEX = 0;
private static CellBordersHandler cellBordersHandler;

View File

@ -1,17 +1,19 @@
package com.baeldung.poi.excel.cellstyle;
import org.apache.poi.ss.usermodel.*;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.junit.Before;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.net.URISyntaxException;
import java.nio.file.Paths;
import static org.junit.Assert.assertEquals;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.IndexedColors;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.junit.Before;
import org.junit.Test;
public class CellStyleHandlerUnitTest {
private static final String FILE_NAME = "cellstyle/CellStyleHandlerTest.xlsx";

View File

@ -0,0 +1,52 @@
package com.baeldung.poi.excel.cellstyle;
import java.io.FileOutputStream;
import java.io.IOException;
import java.net.URISyntaxException;
import java.nio.file.Paths;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.CellStyle;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.junit.Before;
import org.junit.Test;
public class CellStylerUnitTest {
private static String FILE_NAME = "com/baeldung/poi/excel/cellstyle/CellStyle.xlsx";
private static final String NEW_FILE_NAME = "CellStyleTest_output.xlsx";
private String fileLocation;
@Before
public void setup() throws IOException, URISyntaxException {
fileLocation = Paths.get(ClassLoader.getSystemResource(FILE_NAME)
.toURI())
.toString();
}
@Test
public void testApplyWarningColor() throws IOException {
Workbook workbook = new XSSFWorkbook(fileLocation);
Sheet sheet = workbook.getSheetAt(0);
Row row1 = sheet.createRow(0);
row1.setHeightInPoints((short) 40);
CellStyler styler = new CellStyler();
CellStyle style = styler.createWarningColor(workbook);
Cell cell1 = row1.createCell(0);
cell1.setCellStyle(style);
cell1.setCellValue("Hello");
Cell cell2 = row1.createCell(1);
cell2.setCellStyle(style);
cell2.setCellValue("world!");
FileOutputStream outputStream = new FileOutputStream(NEW_FILE_NAME);
workbook.write(outputStream);
outputStream.close();
workbook.close();
}
}

View File

@ -47,7 +47,7 @@
<properties>
<apache-shiro-core-version>1.5.3</apache-shiro-core-version>
<log4j-version>1.2.17</log4j-version>
<log4j.version>2.17.1</log4j.version>
</properties>
</project>

View File

@ -1,9 +1,9 @@
package com.baeldung.differences.rdd;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
import org.apache.commons.io.FileUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.spark.SparkConf;
import org.apache.spark.api.java.JavaRDD;
@ -12,12 +12,15 @@ import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;
import java.io.File;
public class TransformationsUnitTest {
public static final String COMMA_DELIMITER = ",(?=([^\"]*\"[^\"]*\")*[^\"]*$)";
private static JavaSparkContext sc;
private static JavaRDD<String> tourists;
@BeforeClass
public static void init() {
SparkConf conf = new SparkConf().setAppName("uppercaseCountries")
@ -25,8 +28,11 @@ public class TransformationsUnitTest {
sc = new JavaSparkContext(conf);
tourists = sc.textFile("data/Tourist.csv")
.filter(line -> !line.startsWith("Region")); //filter header row
// delete previous output dir and files
FileUtils.deleteQuietly(new File("data/output"));
}
@AfterClass
public static void cleanup() {
sc.close();
@ -39,9 +45,9 @@ public class TransformationsUnitTest {
return columns[1].toUpperCase();
})
.distinct();
upperCaseCountries.saveAsTextFile("data/output/uppercase.txt");
upperCaseCountries.foreach(country -> {
//replace non alphanumerical characters
country = country.replaceAll("[^a-zA-Z]", "");
@ -52,9 +58,9 @@ public class TransformationsUnitTest {
@Test
public void whenFilterByCountry_thenShowRequestedCountryRecords() {
JavaRDD<String> touristsInMexico = tourists.filter(line -> line.split(COMMA_DELIMITER)[1].equals("Mexico"));
touristsInMexico.saveAsTextFile("data/output/touristInMexico.txt");
touristsInMexico.foreach(record -> {
assertEquals("Mexico", record.split(COMMA_DELIMITER)[1]);
});

View File

@ -4,4 +4,5 @@ This module contains articles about Java 15.
### Relevant articles
- [Hidden Classes in Java 15](https://www.baeldung.com/java-hidden-classes)
- [Sealed Classes and Interfaces in Java 15](https://www.baeldung.com/java-sealed-classes-interfaces)

View File

@ -1,5 +1,6 @@
### Relevant articles:
- [An Introduction to InstantSource in Java 17](https://www.baeldung.com/java-instantsource)
- [Pattern Matching for Switch](https://www.baeldung.com/java-switch-pattern-matching)
- [Introduction to HexFormat in Java 17](https://www.baeldung.com/java-hexformat)
- [New Features in Java 17](https://www.baeldung.com/java-17-new-features)

View File

@ -8,4 +8,6 @@ This module contains articles about Java 8 core features
- [Java 8 Stream skip() vs limit()](https://www.baeldung.com/java-stream-skip-vs-limit)
- [Guide to Java BiFunction Interface](https://www.baeldung.com/java-bifunction-interface)
- [Interface With Default Methods vs Abstract Class](https://www.baeldung.com/java-interface-default-method-vs-abstract-class)
- [Convert Between Byte Array and UUID in Java](https://www.baeldung.com/java-byte-array-to-uuid)
- [Create a Simple “Rock-Paper-Scissors” Game in Java](https://www.baeldung.com/java-rock-paper-scissors)
- [[<-- Prev]](/core-java-modules/core-java-8)

View File

@ -0,0 +1,73 @@
package com.baeldung.game;
import java.util.*;
class RockPaperScissorsGame {
enum Move {
ROCK("rock"),
PAPER("paper"),
SCISSORS("scissors");
private String value;
Move(String value) {
this.value = value;
}
public String getValue() {
return value;
}
}
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
int wins = 0;
int losses = 0;
System.out.println("Welcome to Rock-Paper-Scissors! Please enter \"rock\", \"paper\", \"scissors\", or \"quit\" to exit.");
while (true) {
System.out.println("-------------------------");
System.out.print("Enter your move: ");
String playerMove = scanner.nextLine();
if (playerMove.equals("quit")) {
System.out.println("You won " + wins + " times and lost " + losses + " times.");
System.out.println("Thanks for playing! See you again.");
break;
}
if (Arrays.stream(Move.values()).noneMatch(x -> x.getValue().equals(playerMove))) {
System.out.println("Your move isn't valid!");
continue;
}
String computerMove = getComputerMove();
if (playerMove.equals(computerMove)) {
System.out.println("It's a tie!");
} else if (isPlayerWin(playerMove, computerMove)) {
System.out.println("You won!");
wins++;
} else {
System.out.println("You lost!");
losses++;
}
}
}
private static boolean isPlayerWin(String playerMove, String computerMove) {
return playerMove.equals(Move.ROCK.value) && computerMove.equals(Move.SCISSORS.value)
|| (playerMove.equals(Move.SCISSORS.value) && computerMove.equals(Move.PAPER.value))
|| (playerMove.equals(Move.PAPER.value) && computerMove.equals(Move.ROCK.value));
}
private static String getComputerMove() {
Random random = new Random();
int randomNumber = random.nextInt(3);
String computerMove = Move.values()[randomNumber].getValue();
System.out.println("Computer move: " + computerMove);
return computerMove;
}
}

View File

@ -0,0 +1,33 @@
package com.baeldung.uuid;
import java.nio.ByteBuffer;
import java.util.Arrays;
import java.util.UUID;
public class UuidHelper {
public static byte[] convertUUIDToBytes(UUID uuid) {
ByteBuffer bb = ByteBuffer.wrap(new byte[16]);
bb.putLong(uuid.getMostSignificantBits());
bb.putLong(uuid.getLeastSignificantBits());
return bb.array();
}
public static UUID convertBytesToUUID(byte[] bytes) {
ByteBuffer byteBuffer = ByteBuffer.wrap(bytes);
long high = byteBuffer.getLong();
long low = byteBuffer.getLong();
return new UUID(high, low);
}
public static void main(String[] args) {
UUID uuid = UUID.randomUUID();
System.out.println("Original UUID: " + uuid);
byte[] bytes = convertUUIDToBytes(uuid);
System.out.println("Converted byte array: " + Arrays.toString(bytes));
UUID uuidNew = convertBytesToUUID(bytes);
System.out.println("Converted UUID: " + uuidNew);
}
}

View File

@ -22,6 +22,6 @@ class RandomDatesUnitTest {
LocalDate end = LocalDate.now();
LocalDate random = RandomDates.between(start, end);
assertThat(random).isAfter(start).isBefore(end);
assertThat(random).isAfterOrEqualTo(start).isBefore(end);
}
}

View File

@ -34,6 +34,28 @@
</dependency>
</dependencies>
<build>
<finalName>core-java-9-new-features</finalName>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>${maven-compiler-plugin.version}</version>
<configuration>
<source>${maven.compiler.source}</source>
<target>${maven.compiler.target}</target>
</configuration>
</plugin>
</plugins>
</build>
<pluginRepositories>
<pluginRepository>
<id>apache.snapshots</id>
<url>https://repository.apache.org/snapshots/</url>
</pluginRepository>
</pluginRepositories>
<profiles>
<profile>
<id>incubator-features</id>
@ -126,28 +148,6 @@
</profile>
</profiles>
<build>
<finalName>core-java-9-new-features</finalName>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>${maven-compiler-plugin.version}</version>
<configuration>
<source>${maven.compiler.source}</source>
<target>${maven.compiler.target}</target>
</configuration>
</plugin>
</plugins>
</build>
<pluginRepositories>
<pluginRepository>
<id>apache.snapshots</id>
<url>https://repository.apache.org/snapshots/</url>
</pluginRepository>
</pluginRepositories>
<properties>
<rxjava.version>3.0.0</rxjava.version>
<awaitility.version>4.0.2</awaitility.version>

View File

@ -1,17 +1,16 @@
package com.baeldung.collections.iterators;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.concurrent.ConcurrentHashMap;
/**
* Source code https://github.com/eugenp/tutorials
*
* @author Santosh Thakur
*/
public class Iterators {
private static final Logger LOG = LoggerFactory.getLogger(Iterators.class);
public static int failFast1() {
ArrayList<Integer> numbers = new ArrayList<>();
@ -44,7 +43,7 @@ public class Iterators {
}
}
System.out.println("using iterator's remove method = " + numbers);
LOG.debug("using iterator's remove method = {}", numbers);
iterator = numbers.iterator();
while (iterator.hasNext()) {

View File

@ -3,6 +3,8 @@ package com.baeldung.collections.bitset;
import org.junit.Test;
import org.openjdk.jol.info.ClassLayout;
import org.openjdk.jol.info.GraphLayout;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.BitSet;
@ -10,18 +12,20 @@ import static org.assertj.core.api.Assertions.assertThat;
public class BitSetUnitTest {
private static final Logger LOG = LoggerFactory.getLogger(BitSetUnitTest.class);
@Test
public void givenBoolArray_whenMemoryLayout_thenConsumeMoreThanOneBit() {
boolean[] bits = new boolean[1024 * 1024];
System.out.println(ClassLayout.parseInstance(bits).toPrintable());
LOG.debug(ClassLayout.parseInstance(bits).toPrintable());
}
@Test
public void givenBitSet_whenMemoryLayout_thenConsumeOneBitPerFlag() {
BitSet bitSet = new BitSet(1024 * 1024);
System.out.println(GraphLayout.parseInstance(bitSet).toPrintable());
LOG.debug(GraphLayout.parseInstance(bitSet).toPrintable());
}
@Test
@ -157,7 +161,7 @@ public class BitSetUnitTest {
BitSet bitSet = new BitSet();
bitSet.set(15, 25);
bitSet.stream().forEach(System.out::println);
bitSet.stream().forEach(bit -> LOG.debug(String.valueOf(bit)));
assertThat(bitSet.stream().count()).isEqualTo(10);
}

View File

@ -0,0 +1,13 @@
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
</pattern>
</encoder>
</appender>
<root level="INFO">
<appender-ref ref="STDOUT" />
</root>
</configuration>

View File

@ -7,3 +7,4 @@
- [ArrayList vs. LinkedList vs. HashMap in Java](https://www.baeldung.com/java-arraylist-vs-linkedlist-vs-hashmap)
- [Java Deque vs. Stack](https://www.baeldung.com/java-deque-vs-stack)
- [Collection.toArray(new T[0]) or .toArray(new T[size])](https://www.baeldung.com/java-collection-toarray-methods)
- [Create an Empty Map in Java](https://www.baeldung.com/java-create-empty-map)

View File

@ -0,0 +1,56 @@
package com.baeldung.maps.initialize;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.Maps;
import java.util.Collections;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.NavigableMap;
import java.util.SortedMap;
import java.util.TreeMap;
public class EmptyMapInitializer {
public static Map<String, String> articleMap;
static {
articleMap = new HashMap<>();
}
public static Map<String, String> createEmptyMap() {
return Collections.emptyMap();
}
public void createMapUsingConstructors() {
Map hashMap = new HashMap();
Map linkedHashMap = new LinkedHashMap();
Map treeMap = new TreeMap();
}
public Map<String, String> createEmptyMapUsingMapsObject() {
Map<String, String> emptyMap = Maps.newHashMap();
return emptyMap;
}
public Map createGenericEmptyMapUsingMapsObject() {
Map genericEmptyMap = Maps.<String, Integer>newHashMap();
return genericEmptyMap;
}
public static Map<String, String> createMapUsingGuava() {
Map<String, String> emptyMapUsingGuava =
Maps.newHashMap(ImmutableMap.of());
return emptyMapUsingGuava;
}
public SortedMap<String, String> createEmptySortedMap() {
SortedMap<String, String> sortedMap = Collections.emptySortedMap();
return sortedMap;
}
public NavigableMap<String, String> createEmptyNavigableMap() {
NavigableMap<String, String> navigableMap = Collections.emptyNavigableMap();
return navigableMap;
}
}

View File

@ -0,0 +1,31 @@
package com.baeldung.maps.initialize;
import java.util.Map;
import org.junit.Test;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertTrue;
public class EmptyMapInitializerUnitTest {
@Test(expected=UnsupportedOperationException.class)
public void givenEmptyMap_whenAddingEntries_throwsException() {
Map<String, String> map = EmptyMapInitializer.createEmptyMap();
map.put("key", "value");
}
@Test
public void givenEmptyMap_whenChecked_returnsTrue() {
assertTrue(EmptyMapInitializer.articleMap.isEmpty());
}
@Test
public void givenEmptyMap_whenCreatedUsingGuava_returnsEmptyOrNot() {
Map<String, String> emptyMapUsingGuava =
EmptyMapInitializer.createMapUsingGuava();
assertTrue(emptyMapUsingGuava.isEmpty());
emptyMapUsingGuava.put("key", "value");
assertFalse(emptyMapUsingGuava.isEmpty());
}
}

View File

@ -6,3 +6,5 @@ This module contains articles about Map data structures in Java.
- [Using a Custom Class as a Key in a Java HashMap](https://www.baeldung.com/java-custom-class-map-key)
- [Nested HashMaps Examples in Java](https://www.baeldung.com/java-nested-hashmaps)
- [Java HashMap With Different Value Types](https://www.baeldung.com/java-hashmap-different-value-types)
- [Difference Between Map and HashMap in Java](https://www.baeldung.com/java-map-vs-hashmap)
- [How to Create a New Entry in a Map](https://www.baeldung.com/java-map-new-entry)

View File

@ -15,6 +15,16 @@
</parent>
<dependencies>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-collections4</artifactId>
<version>${commons-collections4.version}</version>
</dependency>
<dependency>
<groupId>com.google.guava</groupId>
<artifactId>guava</artifactId>
<version>${guava.version}</version>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
@ -37,12 +47,23 @@
</plugin>
</plugins>
</pluginManagement>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>${maven-compiler-plugin.version}</version>
<configuration>
<source>${maven.compiler.source}</source>
<target>${maven.compiler.target}</target>
</configuration>
</plugin>
</plugins>
</build>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<maven.compiler.source>1.9</maven.compiler.source>
<maven.compiler.target>1.9</maven.compiler.target>
</properties>
</project>

View File

@ -0,0 +1,53 @@
package com.baeldung.entries;
import java.util.Map;
import java.util.Objects;
import java.util.StringJoiner;
public class SimpleCustomKeyValue<K, V> implements Map.Entry<K, V> {
private final K key;
private V value;
public SimpleCustomKeyValue(K key, V value) {
this.key = key;
this.value = value;
}
@Override
public K getKey() {
return key;
}
@Override
public V getValue() {
return value;
}
@Override
public V setValue(V value) {
return this.value = value;
}
@Override
public boolean equals(Object o) {
if (this == o) {
return true;
}
if (o == null || getClass() != o.getClass()) {
return false;
}
SimpleCustomKeyValue<?, ?> that = (SimpleCustomKeyValue<?, ?>) o;
return Objects.equals(key, that.key) && Objects.equals(value, that.value);
}
@Override
public int hashCode() {
return Objects.hash(key, value);
}
@Override
public String toString() {
return new StringJoiner(", ", SimpleCustomKeyValue.class.getSimpleName() + "[", "]").add("key=" + key).add("value=" + value).toString();
}
}

View File

@ -0,0 +1,25 @@
package com.baeldung.mapandhashmap;
import com.baeldung.mapandhashmap.printer.HashMapPrinter;
import com.baeldung.mapandhashmap.printer.MapPrinter;
import java.util.HashMap;
import java.util.Map;
import java.util.TreeMap;
public class Main {
public static void main(String[] args) {
Map<String, String> map = new HashMap<>();
HashMap<String, String> hashMap = new HashMap<>();
TreeMap<String, String> treeMap = new TreeMap<>();
HashMapPrinter hashMapPrinter = new HashMapPrinter();
hashMapPrinter.printMap(hashMap);
// hashMapPrinter.printMap(treeMap); Compile time error
// hashMapPrinter.printMap(map); Compile time error
MapPrinter mapPrinter = new MapPrinter();
mapPrinter.printMap(hashMap);
mapPrinter.printMap(treeMap);
mapPrinter.printMap(map);
}
}

View File

@ -0,0 +1,13 @@
package com.baeldung.mapandhashmap.printer;
import java.util.HashMap;
import java.util.Map.Entry;
public class HashMapPrinter {
public void printMap(final HashMap<?, ?> map) {
for (final Entry<?, ?> entry : map.entrySet()) {
System.out.println(entry.getKey() + " " + entry.getValue());
}
}
}

View File

@ -0,0 +1,13 @@
package com.baeldung.mapandhashmap.printer;
import java.util.Map;
import java.util.Map.Entry;
public class MapPrinter {
public void printMap(final Map<?, ?> map) {
for (final Entry<?, ?> entry : map.entrySet()) {
System.out.println(entry.getKey() + " " + entry.getValue());
}
}
}

View File

@ -0,0 +1,19 @@
package com.baeldung.mapandhashmap.printer;
import java.util.Map;
import java.util.Map.Entry;
public class MapReporter {
private final Map<?, ?> map;
public MapReporter(final Map<?, ?> map) {
this.map = map;
}
public void printMap() {
for (final Entry<?, ?> entry : this.map.entrySet()) {
System.out.println(entry.getKey() + " " + entry.getValue());
}
}
}

View File

@ -0,0 +1,113 @@
package com.baeldung.entries;
import com.google.common.collect.Maps;
import org.apache.commons.collections4.KeyValue;
import org.apache.commons.collections4.keyvalue.DefaultMapEntry;
import org.apache.commons.collections4.keyvalue.UnmodifiableMapEntry;
import org.junit.jupiter.api.Test;
import java.util.AbstractMap;
import java.util.Map;
import java.util.stream.Stream;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.tuple;
public class EntriesExampleUnitTest {
@Test
public void givenEntries_whenVerifying_thenShouldContainKeyValues() {
AbstractMap.SimpleEntry<String, String> firstEntry = new AbstractMap.SimpleEntry<>("key1", "value1");
AbstractMap.SimpleEntry<String, String> secondEntry = new AbstractMap.SimpleEntry<>("key2", "value2");
AbstractMap.SimpleEntry<String, String> thirdEntry = new AbstractMap.SimpleEntry<>(firstEntry);
thirdEntry.setValue("a different value");
assertThat(Stream.of(firstEntry, secondEntry, thirdEntry))
.extracting("key", "value")
.containsExactly(
tuple("key1", "value1"),
tuple("key2", "value2"),
tuple("key1", "a different value"));
}
@Test
public void givenImmutableEntries_whenVerifying_thenShouldContainKeyValues() {
AbstractMap.SimpleImmutableEntry<String, String> firstEntry = new AbstractMap.SimpleImmutableEntry<>("key1", "value1");
AbstractMap.SimpleImmutableEntry<String, String> secondEntry = new AbstractMap.SimpleImmutableEntry<>("key2", "value2");
AbstractMap.SimpleImmutableEntry<String, String> thirdEntry = new AbstractMap.SimpleImmutableEntry<>(firstEntry);
assertThat(Stream.of(firstEntry, secondEntry, thirdEntry))
.extracting("key", "value")
.containsExactly(
tuple("key1", "value1"),
tuple("key2", "value2"),
tuple("key1", "value1"));
}
@Test
public void givenImmutableEntryUsingJava9_whenVerifying_thenShouldContainKeyValues() {
Map.Entry<String, String> entry = Map.entry("key", "value");
assertThat(entry.getKey())
.isEqualTo("key");
assertThat(entry.getValue())
.isEqualTo("value");
}
@Test
public void givenEntriesWithApacheCommons_whenVerifying_thenShouldContainKeyValues() {
Map.Entry<String, String> firstEntry = new DefaultMapEntry<>("key1", "value1");
KeyValue<String, String> secondEntry = new DefaultMapEntry<>("key2", "value2");
KeyValue<String, String> thirdEntry = new DefaultMapEntry<>(firstEntry);
KeyValue<String, String> fourthEntry = new DefaultMapEntry<>(secondEntry);
firstEntry.setValue("a different value");
assertThat(firstEntry)
.extracting("key", "value")
.containsExactly("key1", "a different value");
assertThat(Stream.of(secondEntry, thirdEntry, fourthEntry))
.extracting("key", "value")
.containsExactly(
tuple("key2", "value2"),
tuple("key1", "value1"),
tuple("key2", "value2"));
}
@Test
public void givenImmutableEntriesWithApacheCommons_whenVerifying_thenShouldContainKeyValues() {
Map.Entry<String, String> firstEntry = new UnmodifiableMapEntry<>("key1", "value1");
KeyValue<String, String> secondEntry = new UnmodifiableMapEntry<>("key2", "value2");
KeyValue<String, String> thirdEntry = new UnmodifiableMapEntry<>(firstEntry);
KeyValue<String, String> fourthEntry = new UnmodifiableMapEntry<>(secondEntry);
assertThat(firstEntry)
.extracting("key", "value")
.containsExactly("key1", "value1");
assertThat(Stream.of(secondEntry, thirdEntry, fourthEntry))
.extracting("key", "value")
.containsExactly(
tuple("key2", "value2"),
tuple("key1", "value1"),
tuple("key2", "value2"));
}
@Test
public void givenImmutableEntriesWithGuava_whenVerifying_thenShouldContainKeyValues() {
Map.Entry<String, String> firstEntry = Maps.immutableEntry("key1", "value1");
Map.Entry<String, String> secondEntry = Maps.immutableEntry("key2", "value2");
assertThat(Stream.of(firstEntry, secondEntry))
.extracting("key", "value")
.containsExactly(
tuple("key1", "value1"),
tuple("key2", "value2"));
}
}

View File

@ -0,0 +1,31 @@
package com.baeldung.entries;
import com.google.common.collect.ImmutableMap;
import org.junit.jupiter.api.Test;
import java.util.Map;
import java.util.stream.Stream;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.tuple;
class SimpleCustomKeyValueUnitTest {
@Test
public void givenModifiableEntries_whenVerifying_thenShouldContainKeyValues() {
Map.Entry<String, String> firstEntry = new SimpleCustomKeyValue<>("key1", "value1");
Map.Entry<String, String> secondEntry = new SimpleCustomKeyValue<>("key2", "value2");
secondEntry.setValue("different value");
Map<String, String> map = Map.ofEntries(firstEntry, secondEntry);
assertThat(map)
.isEqualTo(ImmutableMap.<String,String>builder()
.put("key1", "value1")
.put("key2", "different value")
.build());
}
}

View File

@ -0,0 +1,56 @@
package com.baeldung.mapandhashmap.printer;
import static org.assertj.core.api.AssertionsForClassTypes.assertThat;
import java.io.ByteArrayOutputStream;
import java.io.PrintStream;
import java.util.HashMap;
import java.util.LinkedHashMap;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
class HashMapPrinterUnitTest {
private final HashMapPrinter mapPrinter = new HashMapPrinter();
private final ByteArrayOutputStream outputStreamCaptor = new ByteArrayOutputStream();
@BeforeEach
public void setUp() {
System.setOut(new PrintStream(outputStreamCaptor));
}
@Test
@DisplayName("Test hash map printer with HashMap")
void testPrintHashMap() {
// given
String key = "HashMap";
String value = "Main default implementation for the Map interface";
String expected = key + " " + value;
HashMap<String, String> map = new HashMap<>();
map.put(key, value);
// when
mapPrinter.printMap(map);
// then
String actual = outputStreamCaptor.toString().trim();
assertThat(actual).isEqualTo(expected);
}
@Test
@DisplayName("Test hash map printer with LinkedHash")
void testPrintLinkedHashMap() {
// given
String key = "LinkedHashMap";
String value = "Use this implementation if you need keep the order of elements";
String expected = key + " " + value;
LinkedHashMap<String, String> map = new LinkedHashMap<>();
map.put(key, value);
// when
mapPrinter.printMap(map);
// then
String actual = outputStreamCaptor.toString().trim();
assertThat(actual).isEqualTo(expected);
}
}

View File

@ -0,0 +1,71 @@
package com.baeldung.mapandhashmap.printer;
import static org.assertj.core.api.AssertionsForClassTypes.assertThat;
import java.io.ByteArrayOutputStream;
import java.io.PrintStream;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.TreeMap;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
class MapPrinterUnitTest {
private final MapPrinter mapPrinter = new MapPrinter();
private final ByteArrayOutputStream outputStreamCaptor = new ByteArrayOutputStream();
@BeforeEach
public void setUp() {
System.setOut(new PrintStream(outputStreamCaptor));
}
@Test
@DisplayName("Test printer with TreeMap")
void testPrintTreeMap() {
// given
String key = "TreeMap";
String value = "Used when sorting is needed";
String expected = key + " " + value;
TreeMap<String, String> map = new TreeMap<>();
map.put(key, value);
// when
mapPrinter.printMap(map);
// then
String actual = outputStreamCaptor.toString().trim();
assertThat(actual).isEqualTo(expected);
}
@Test
@DisplayName("Test printer with HashMap")
void testPrintHashMap() {
// given
String key = "HashMap";
String value = "Main default implementation for the Map interface";
String expected = key + " " + value;
HashMap<String, String> map = new HashMap<>();
map.put(key, value);
// when
mapPrinter.printMap(map);
// then
String actual = outputStreamCaptor.toString().trim();
assertThat(actual).isEqualTo(expected);
}
@Test
@DisplayName("Test printer with LinkedHash")
void testPrintLinkedHashMap() {
// given
String key = "LinkedHashMap";
String value = "Use this implementation if you need keep the order of elements";
String expected = key + " " + value;
LinkedHashMap<String, String> map = new LinkedHashMap<>();
map.put(key, value);
// when
mapPrinter.printMap(map);
// then
String actual = outputStreamCaptor.toString().trim();
assertThat(actual).isEqualTo(expected);
}
}

View File

@ -0,0 +1,74 @@
package com.baeldung.mapandhashmap.printer;
import static org.assertj.core.api.AssertionsForClassTypes.assertThat;
import java.io.ByteArrayOutputStream;
import java.io.PrintStream;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.TreeMap;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
class MapReporterUnitTest {
private final ByteArrayOutputStream outputStreamCaptor = new ByteArrayOutputStream();
@BeforeEach
public void setUp() {
System.setOut(new PrintStream(outputStreamCaptor));
}
@Test
@DisplayName("Test reporter with TreeMap")
void testPrintTreeMap() {
// given
String key = "TreeMap";
String value = "Used when sorting is needed";
String expected = key + " " + value;
TreeMap<String, String> map = new TreeMap<>();
map.put(key, value);
// when
MapReporter mapReporter = new MapReporter(map);
mapReporter.printMap();
// then
String actual = outputStreamCaptor.toString().trim();
assertThat(actual).isEqualTo(expected);
}
@Test
@DisplayName("Test reporter with HashMap")
void testPrintHashMap() {
// given
String key = "HashMap";
String value = "Main default implementation for the Map interface";
String expected = key + " " + value;
HashMap<String, String> map = new HashMap<>();
map.put(key, value);
// when
MapReporter mapReporter = new MapReporter(map);
mapReporter.printMap();
// then
String actual = outputStreamCaptor.toString().trim();
assertThat(actual).isEqualTo(expected);
}
@Test
@DisplayName("Test reporter with LinkedHash")
void testPrintLinkedHashMap() {
// given
String key = "LinkedHashMap";
String value = "Use this implementation if you need keep the order of elements";
String expected = key + " " + value;
LinkedHashMap<String, String> map = new LinkedHashMap<>();
map.put(key, value);
// when
MapReporter mapReporter = new MapReporter(map);
mapReporter.printMap();
// then
String actual = outputStreamCaptor.toString().trim();
assertThat(actual).isEqualTo(expected);
}
}

View File

@ -1,9 +1,15 @@
package com.baeldung.concurrent.prioritytaskexecution;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Job implements Runnable {
private String jobName;
private JobPriority jobPriority;
private static final Logger LOGGER = LoggerFactory.getLogger(Job.class);
private final String jobName;
private final JobPriority jobPriority;
public Job(String jobName, JobPriority jobPriority) {
this.jobName = jobName;
this.jobPriority = jobPriority != null ? jobPriority : JobPriority.MEDIUM;
@ -16,8 +22,7 @@ public class Job implements Runnable {
@Override
public void run() {
try {
System.out.println("Job:" + jobName +
" Priority:" + jobPriority);
LOGGER.debug("Job:{} Priority:{}", jobName, jobPriority);
Thread.sleep(1000);
} catch (InterruptedException ignored) {
}

View File

@ -1,19 +1,21 @@
package com.baeldung.forkjoin;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.concurrent.ForkJoinTask;
import java.util.concurrent.RecursiveAction;
import java.util.logging.Logger;
public class CustomRecursiveAction extends RecursiveAction {
final Logger logger = LoggerFactory.getLogger(CustomRecursiveAction.class);
private String workLoad = "";
private static final int THRESHOLD = 4;
private static Logger logger = Logger.getAnonymousLogger();
public CustomRecursiveAction(String workLoad) {
this.workLoad = workLoad;
}
@ -43,7 +45,7 @@ public class CustomRecursiveAction extends RecursiveAction {
private void processing(String work) {
String result = work.toUpperCase();
logger.info("This result - (" + result + ") - was processed by " + Thread.currentThread()
logger.debug("This result - (" + result + ") - was processed by " + Thread.currentThread()
.getName());
}
}

View File

@ -3,9 +3,9 @@ package com.baeldung.concurrent.prioritytaskexecution;
import org.junit.Test;
public class PriorityJobSchedulerUnitTest {
private static int POOL_SIZE = 1;
private static int QUEUE_SIZE = 10;
private static final int POOL_SIZE = 1;
private static final int QUEUE_SIZE = 10;
@Test
public void whenMultiplePriorityJobsQueued_thenHighestPriorityJobIsPicked() {
Job job1 = new Job("Job1", JobPriority.LOW);
@ -14,19 +14,19 @@ public class PriorityJobSchedulerUnitTest {
Job job4 = new Job("Job4", JobPriority.MEDIUM);
Job job5 = new Job("Job5", JobPriority.LOW);
Job job6 = new Job("Job6", JobPriority.HIGH);
PriorityJobScheduler pjs = new PriorityJobScheduler(POOL_SIZE, QUEUE_SIZE);
pjs.scheduleJob(job1);
pjs.scheduleJob(job2);
pjs.scheduleJob(job3);
pjs.scheduleJob(job4);
pjs.scheduleJob(job5);
pjs.scheduleJob(job6);
// ensure no tasks is pending before closing the scheduler
while (pjs.getQueuedTaskCount() != 0);
// delay to avoid job sleep (added for demo) being interrupted
try {
Thread.sleep(2000);
@ -34,7 +34,7 @@ public class PriorityJobSchedulerUnitTest {
Thread.currentThread().interrupt();
throw new RuntimeException(e);
}
pjs.closeScheduler();
}
}

View File

@ -1,18 +1,15 @@
package com.baeldung.forkjoin;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
import com.baeldung.forkjoin.util.PoolUtil;
import org.junit.Before;
import org.junit.Test;
import java.util.Random;
import java.util.concurrent.ForkJoinPool;
import org.junit.Before;
import org.junit.Test;
import com.baeldung.forkjoin.CustomRecursiveAction;
import com.baeldung.forkjoin.CustomRecursiveTask;
import com.baeldung.forkjoin.util.PoolUtil;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
public class Java8ForkJoinIntegrationTest {
@ -63,11 +60,11 @@ public class Java8ForkJoinIntegrationTest {
ForkJoinPool forkJoinPool = ForkJoinPool.commonPool();
forkJoinPool.execute(customRecursiveTask);
int result = customRecursiveTask.join();
customRecursiveTask.join();
assertTrue(customRecursiveTask.isDone());
forkJoinPool.submit(customRecursiveTask);
int resultTwo = customRecursiveTask.join();
customRecursiveTask.join();
assertTrue(customRecursiveTask.isDone());
}

View File

@ -1,12 +1,12 @@
package com.baeldung.thread.join;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
import java.util.logging.Logger;
import org.junit.Ignore;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
/**
* Demonstrates Thread.join behavior.
@ -14,55 +14,55 @@ import org.junit.Test;
*/
public class ThreadJoinUnitTest {
final static Logger LOGGER = Logger.getLogger(ThreadJoinUnitTest.class.getName());
private static final Logger LOGGER = LoggerFactory.getLogger(ThreadJoinUnitTest.class);
class SampleThread extends Thread {
public int processingCount = 0;
static class SampleThread extends Thread {
public int processingCount;
SampleThread(int processingCount) {
this.processingCount = processingCount;
LOGGER.info("Thread " + this.getName() + " created");
LOGGER.debug("Thread " + this.getName() + " created");
}
@Override
public void run() {
LOGGER.info("Thread " + this.getName() + " started");
LOGGER.debug("Thread " + this.getName() + " started");
while (processingCount > 0) {
try {
Thread.sleep(1000); // Simulate some work being done by thread
} catch (InterruptedException e) {
LOGGER.info("Thread " + this.getName() + " interrupted.");
LOGGER.debug("Thread " + this.getName() + " interrupted.");
}
processingCount--;
LOGGER.info("Inside Thread " + this.getName() + ", processingCount = " + processingCount);
LOGGER.debug("Inside Thread " + this.getName() + ", processingCount = " + processingCount);
}
LOGGER.info("Thread " + this.getName() + " exiting");
LOGGER.debug("Thread " + this.getName() + " exiting");
}
}
@Test
public void givenNewThread_whenJoinCalled_returnsImmediately() throws InterruptedException {
Thread t1 = new SampleThread(0);
LOGGER.info("Invoking join.");
LOGGER.debug("Invoking join.");
t1.join();
LOGGER.info("Returned from join");
LOGGER.info("Thread state is" + t1.getState());
LOGGER.debug("Returned from join");
LOGGER.debug("Thread state is" + t1.getState());
assertFalse(t1.isAlive());
}
@Test
public void givenStartedThread_whenJoinCalled_waitsTillCompletion()
public void givenStartedThread_whenJoinCalled_waitsTillCompletion()
throws InterruptedException {
Thread t2 = new SampleThread(1);
t2.start();
LOGGER.info("Invoking join.");
LOGGER.debug("Invoking join.");
t2.join();
LOGGER.info("Returned from join");
LOGGER.debug("Returned from join");
assertFalse(t2.isAlive());
}
@Test
public void givenStartedThread_whenTimedJoinCalled_waitsUntilTimedout()
public void givenStartedThread_whenTimedJoinCalled_waitsUntilTimedout()
throws InterruptedException {
Thread t3 = new SampleThread(10);
t3.start();
@ -72,18 +72,18 @@ public class ThreadJoinUnitTest {
@Test
@Ignore
public void givenThreadTerminated_checkForEffect_notGuaranteed()
public void givenThreadTerminated_checkForEffect_notGuaranteed()
throws InterruptedException {
SampleThread t4 = new SampleThread(10);
t4.start();
//not guaranteed to stop even if t4 finishes.
do {
} while (t4.processingCount > 0);
} while (t4.processingCount > 0);
}
@Test
public void givenJoinWithTerminatedThread_checkForEffect_guaranteed()
public void givenJoinWithTerminatedThread_checkForEffect_guaranteed()
throws InterruptedException {
SampleThread t4 = new SampleThread(10);
t4.start();

View File

@ -0,0 +1,13 @@
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
</pattern>
</encoder>
</appender>
<root level="INFO">
<appender-ref ref="STDOUT"/>
</root>
</configuration>

View File

@ -1,25 +1,22 @@
package com.baeldung.atomicstampedreference;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.concurrent.atomic.AtomicStampedReference;
public class StampedAccount {
private AtomicInteger stamp = new AtomicInteger(0);
private AtomicStampedReference<Integer> account = new AtomicStampedReference<>(0, 0);
public int getBalance() {
return account.getReference();
}
public int getStamp() {
return account.getStamp();
}
private final AtomicInteger stamp = new AtomicInteger(0);
private final AtomicStampedReference<Integer> account = new AtomicStampedReference<>(0, 0);
public boolean deposit(int funds) {
int[] stamps = new int[1];
int current = this.account.get(stamps);
int newStamp = this.stamp.incrementAndGet();
// Thread is paused here to allow other threads to update the stamp and amount (for testing only)
sleep();
return this.account.compareAndSet(current, current + funds, stamps[0], newStamp);
}
@ -29,4 +26,19 @@ public class StampedAccount {
int newStamp = this.stamp.incrementAndGet();
return this.account.compareAndSet(current, current - funds, stamps[0], newStamp);
}
public int getBalance() {
return account.getReference();
}
public int getStamp() {
return account.getStamp();
}
private static void sleep() {
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException ignored) {
}
}
}

View File

@ -1,21 +1,38 @@
package com.baeldung.atomicstampedreference;
import org.junit.Assert;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
public class ThreadStampedAccountUnitTest {
@Test
public void givenMultiThread_whenStampedAccount_thenSetBalance() throws InterruptedException {
StampedAccount account = new StampedAccount();
Thread t = new Thread(() -> {
while (!account.withdrawal(100))
while (!account.deposit(100)) {
Thread.yield();
}
});
t.start();
Assert.assertTrue(account.deposit(100));
t.join(1_000);
Assert.assertFalse(t.isAlive());
Assert.assertSame(0, account.getBalance());
Thread t2 = new Thread(() -> {
while (!account.withdrawal(100)) {
Thread.yield();
}
});
t2.start();
t.join(10_000);
t2.join(10_000);
assertFalse(t.isAlive());
assertFalse(t2.isAlive());
assertEquals(0, account.getBalance());
assertTrue(account.getStamp() > 0);
}
}

View File

@ -4,3 +4,4 @@
- [Bad Practices With Synchronization](https://www.baeldung.com/java-synchronization-bad-practices)
- [Start Two Threads at the Exact Same Time in Java](https://www.baeldung.com/java-start-two-threads-at-same-time)
- [Volatile Variables and Thread Safety](https://www.baeldung.com/java-volatile-variables-thread-safety)
- [Producer-Consumer Problem With Example in Java](https://www.baeldung.com/java-producer-consumer-problem)

View File

@ -0,0 +1,43 @@
package com.baeldung.lockbykey;
/**
* This class shows examples of how you should use the lock
*
*/
public class ExampleUsage {
void doWithSimpleExclusiveLock(String key) {
SimpleExclusiveLockByKey simpleExclusiveLockByKey = new SimpleExclusiveLockByKey();
if (simpleExclusiveLockByKey.tryLock(key)) {
try {
// do stuff
} finally {
// it is very important to unlock in the finally block to avoid locking keys forever
simpleExclusiveLockByKey.unlock(key);
}
}
}
// A concrete example can be found in the unit tests
void doWithLock(String key) {
LockByKey lockByKey = new LockByKey();
lockByKey.lock(key);
try {
// do stuff
} finally {
lockByKey.unlock(key);
}
}
// It works exactly the same as with locks
void doWithSemaphore(String key) {
SimultaneousEntriesLockByKey lockByKey = new SimultaneousEntriesLockByKey();
lockByKey.lock(key);
try {
// do stuff
} finally {
lockByKey.unlock(key);
}
}
}

View File

@ -0,0 +1,41 @@
package com.baeldung.lockbykey;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;
public class LockByKey {
private static class LockWrapper {
private final Lock lock = new ReentrantLock();
private final AtomicInteger numberOfThreadsInQueue = new AtomicInteger(1);
private LockWrapper addThreadInQueue() {
numberOfThreadsInQueue.incrementAndGet();
return this;
}
private int removeThreadFromQueue() {
return numberOfThreadsInQueue.decrementAndGet();
}
}
private static ConcurrentHashMap<String, LockWrapper> locks = new ConcurrentHashMap<String, LockWrapper>();
public void lock(String key) {
LockWrapper lockWrapper = locks.compute(key, (k, v) -> v == null ? new LockWrapper() : v.addThreadInQueue());
lockWrapper.lock.lock();
}
public void unlock(String key) {
LockWrapper lockWrapper = locks.get(key);
lockWrapper.lock.unlock();
if (lockWrapper.removeThreadFromQueue() == 0) {
// NB : We pass in the specific value to remove to handle the case where another thread would queue right before the removal
locks.remove(key, lockWrapper);
}
}
}

View File

@ -0,0 +1,18 @@
package com.baeldung.lockbykey;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
public class SimpleExclusiveLockByKey {
private static Set<String> usedKeys= ConcurrentHashMap.newKeySet();
public boolean tryLock(String key) {
return usedKeys.add(key);
}
public void unlock(String key) {
usedKeys.remove(key);
}
}

View File

@ -0,0 +1,25 @@
package com.baeldung.lockbykey;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.Semaphore;
public class SimultaneousEntriesLockByKey {
private static final int ALLOWED_THREADS = 2;
private static ConcurrentHashMap<String, Semaphore> semaphores = new ConcurrentHashMap<String, Semaphore>();
public void lock(String key) {
Semaphore semaphore = semaphores.compute(key, (k, v) -> v == null ? new Semaphore(ALLOWED_THREADS) : v);
semaphore.acquireUninterruptibly();
}
public void unlock(String key) {
Semaphore semaphore = semaphores.get(key);
semaphore.release();
if (semaphore.availablePermits() == ALLOWED_THREADS) {
semaphores.remove(key, semaphore);
}
}
}

View File

@ -0,0 +1,106 @@
package com.baeldung.lockbykey;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertTrue;
import java.util.concurrent.atomic.AtomicBoolean;
import org.junit.jupiter.api.Test;
public class LockByKeyUnitTest {
@Test
void givenNoLockedKey_WhenLock_ThenSuccess() throws InterruptedException {
AtomicBoolean threadWasExecuted = new AtomicBoolean(false);
Thread thread = new Thread(() -> {
String key = "key";
LockByKey lockByKey = new LockByKey();
lockByKey.lock(key);
try {
threadWasExecuted.set(true);
} finally {
lockByKey.unlock(key);
}
});
try {
thread.start();
Thread.sleep(100);
} finally {
assertTrue(threadWasExecuted.get());
}
}
@Test
void givenLockedKey_WhenLock_ThenFailure() throws InterruptedException {
String key = "key";
LockByKey lockByKey = new LockByKey();
lockByKey.lock(key);
AtomicBoolean anotherThreadWasExecuted = new AtomicBoolean(false);
Thread threadLockingOnAnotherKey = new Thread(() -> {
LockByKey otherLockByKey = new LockByKey();
otherLockByKey.lock(key);
try {
anotherThreadWasExecuted.set(true);
} finally {
otherLockByKey.unlock(key);
}
});
try {
threadLockingOnAnotherKey.start();
Thread.sleep(100);
} finally {
assertFalse(anotherThreadWasExecuted.get());
lockByKey.unlock(key);
}
}
@Test
void givenAnotherKeyLocked_WhenLock_ThenSuccess() throws InterruptedException {
String key = "key";
LockByKey lockByKey = new LockByKey();
lockByKey.lock(key);
AtomicBoolean anotherThreadWasExecuted = new AtomicBoolean(false);
Thread threadLockingOnAnotherKey = new Thread(() -> {
String anotherKey = "anotherKey";
LockByKey otherLockByKey = new LockByKey();
otherLockByKey.lock(anotherKey);
try {
anotherThreadWasExecuted.set(true);
} finally {
otherLockByKey.unlock(anotherKey);
}
});
try {
threadLockingOnAnotherKey.start();
Thread.sleep(100);
} finally {
assertTrue(anotherThreadWasExecuted.get());
lockByKey.unlock(key);
}
}
@Test
void givenUnlockedKey_WhenLock_ThenSuccess() throws InterruptedException {
String key = "key";
LockByKey lockByKey = new LockByKey();
lockByKey.lock(key);
AtomicBoolean anotherThreadWasExecuted = new AtomicBoolean(false);
Thread threadLockingOnAnotherKey = new Thread(() -> {
LockByKey otherLockByKey = new LockByKey();
otherLockByKey.lock(key);
try {
anotherThreadWasExecuted.set(true);
} finally {
otherLockByKey.unlock(key);
}
});
try {
lockByKey.unlock(key);
threadLockingOnAnotherKey.start();
Thread.sleep(100);
} finally {
assertTrue(anotherThreadWasExecuted.get());
}
}
}

View File

@ -0,0 +1,51 @@
package com.baeldung.lockbykey;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertTrue;
import java.lang.reflect.Field;
import java.util.concurrent.ConcurrentHashMap;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
public class SimpleExclusiveLockByKeyUnitTest {
@BeforeEach
void cleanUpLocks() throws Exception {
Field field = SimpleExclusiveLockByKey.class.getDeclaredField("usedKeys");
field.setAccessible(true);
field.set(null, ConcurrentHashMap.newKeySet());
}
@Test
void givenNoLockedKey_WhenTryLock_ThenSuccess() {
SimpleExclusiveLockByKey lockByKey = new SimpleExclusiveLockByKey();
assertTrue(lockByKey.tryLock("key"));
}
@Test
void givenLockedKey_WhenTryLock_ThenFailure() {
String key = "key";
SimpleExclusiveLockByKey lockByKey = new SimpleExclusiveLockByKey();
lockByKey.tryLock(key);
assertFalse(lockByKey.tryLock(key));
}
@Test
void givenAnotherKeyLocked_WhenTryLock_ThenSuccess() {
SimpleExclusiveLockByKey lockByKey = new SimpleExclusiveLockByKey();
lockByKey.tryLock("other");
assertTrue(lockByKey.tryLock("key"));
}
@Test
void givenUnlockedKey_WhenTryLock_ThenSuccess() {
String key = "key";
SimpleExclusiveLockByKey lockByKey = new SimpleExclusiveLockByKey();
lockByKey.tryLock(key);
lockByKey.unlock(key);
assertTrue(lockByKey.tryLock(key));
}
}

View File

@ -0,0 +1,146 @@
package com.baeldung.lockbykey;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertTrue;
import java.util.concurrent.atomic.AtomicBoolean;
import org.junit.jupiter.api.Test;
public class SimultaneousEntriesLockByKeyUnitTest {
@Test
void givenNoKeyUsed_WhenLock_ThenSuccess() throws InterruptedException {
AtomicBoolean threadWasExecuted = new AtomicBoolean(false);
Thread thread = new Thread(() -> {
String key = "key";
SimultaneousEntriesLockByKey lockByKey = new SimultaneousEntriesLockByKey();
lockByKey.lock(key);
try {
threadWasExecuted.set(true);
} finally {
lockByKey.unlock(key);
}
});
try {
thread.start();
Thread.sleep(100);
} finally {
assertTrue(threadWasExecuted.get());
}
}
@Test
void givenKeyLockedWithRemainingPermits_WhenLock_ThenSuccess() throws InterruptedException {
String key = "key";
SimultaneousEntriesLockByKey lockByKey = new SimultaneousEntriesLockByKey();
lockByKey.lock(key);
AtomicBoolean anotherThreadWasExecuted = new AtomicBoolean(false);
Thread threadLockingOnAnotherKey = new Thread(() -> {
SimultaneousEntriesLockByKey otherLockByKeyWithSemaphore = new SimultaneousEntriesLockByKey();
otherLockByKeyWithSemaphore.lock(key);
try {
anotherThreadWasExecuted.set(true);
} finally {
otherLockByKeyWithSemaphore.unlock(key);
}
});
try {
threadLockingOnAnotherKey.start();
Thread.sleep(100);
} finally {
assertTrue(anotherThreadWasExecuted.get());
lockByKey.unlock(key);
}
}
@Test
void givenKeyLockedWithNoRemainingPermits_WhenLock_ThenFailure() throws InterruptedException {
String key = "key";
SimultaneousEntriesLockByKey lockByKey = new SimultaneousEntriesLockByKey();
lockByKey.lock(key);
AtomicBoolean anotherThreadWasExecuted = new AtomicBoolean(false);
Thread threadLockingOnAnotherKey1 = new Thread(() -> {
SimultaneousEntriesLockByKey otherLockByKeyWithSemaphore = new SimultaneousEntriesLockByKey();
otherLockByKeyWithSemaphore.lock(key);
try {
Thread.sleep(200); // make sure this thread will release the lock after the assertion
} catch (InterruptedException e) {
} finally {
otherLockByKeyWithSemaphore.unlock(key);
}
});
Thread threadLockingOnAnotherKey2 = new Thread(() -> {
SimultaneousEntriesLockByKey otherLockByKey = new SimultaneousEntriesLockByKey();
try {
Thread.sleep(50); // make sure thread1 will acquire the key first
} catch (InterruptedException e) {
}
otherLockByKey.lock(key);
try {
anotherThreadWasExecuted.set(true);
} finally {
otherLockByKey.unlock(key);
}
});
try {
threadLockingOnAnotherKey1.start();
threadLockingOnAnotherKey2.start();
Thread.sleep(100);
} finally {
assertFalse(anotherThreadWasExecuted.get());
lockByKey.unlock(key);
}
}
@Test
void givenAnotherKeyLocked_WhenLock_ThenSuccess() throws InterruptedException {
String key = "key";
SimultaneousEntriesLockByKey lockByKey = new SimultaneousEntriesLockByKey();
lockByKey.lock(key);
AtomicBoolean anotherThreadWasExecuted = new AtomicBoolean(false);
Thread threadLockingOnAnotherKey = new Thread(() -> {
String anotherKey = "anotherKey";
SimultaneousEntriesLockByKey otherLockByKey = new SimultaneousEntriesLockByKey();
otherLockByKey.lock(anotherKey);
try {
anotherThreadWasExecuted.set(true);
} finally {
otherLockByKey.unlock(anotherKey);
}
});
try {
threadLockingOnAnotherKey.start();
Thread.sleep(100);
} finally {
assertTrue(anotherThreadWasExecuted.get());
lockByKey.unlock(key);
}
}
@Test
void givenUnlockedKey_WhenLock_ThenSuccess() throws InterruptedException {
String key = "key";
SimultaneousEntriesLockByKey lockByKey = new SimultaneousEntriesLockByKey();
lockByKey.lock(key);
AtomicBoolean anotherThreadWasExecuted = new AtomicBoolean(false);
Thread threadLockingOnAnotherKey = new Thread(() -> {
SimultaneousEntriesLockByKey otherLockByKey = new SimultaneousEntriesLockByKey();
otherLockByKey.lock(key);
try {
anotherThreadWasExecuted.set(true);
} finally {
otherLockByKey.unlock(key);
}
});
try {
lockByKey.unlock(key);
threadLockingOnAnotherKey.start();
Thread.sleep(100);
} finally {
assertTrue(anotherThreadWasExecuted.get());
}
}
}

View File

@ -16,12 +16,17 @@ class LongRunningAction implements Runnable {
public void run() {
System.out.println("This is phase " + ph.getPhase());
System.out.println("Thread " + threadName + " before long running action");
ph.arriveAndAwaitAdvance();
try {
Thread.sleep(20);
Thread.sleep(2000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("Thread " + threadName + " action completed and waiting for others");
ph.arriveAndAwaitAdvance();
System.out.println("Thread " + threadName + " proceeding in phase " + ph.getPhase());
ph.arriveAndDeregister();
}
}

View File

@ -26,13 +26,20 @@ public class PhaserUnitTest {
executorService.submit(new LongRunningAction("thread-3", ph));
//then
System.out.println("Thread " + Thread.currentThread().getName() + " waiting for others");
ph.arriveAndAwaitAdvance();
System.out.println("Thread " + Thread.currentThread().getName() + " proceeding in phase " + ph.getPhase());
assertEquals(1, ph.getPhase());
//and
executorService.submit(new LongRunningAction("thread-4", ph));
executorService.submit(new LongRunningAction("thread-5", ph));
System.out.println("Thread " + Thread.currentThread().getName() + " waiting for others");
ph.arriveAndAwaitAdvance();
System.out.println("Thread " + Thread.currentThread().getName() + " proceeding in phase " + ph.getPhase());
assertEquals(2, ph.getPhase());

View File

@ -12,7 +12,6 @@ This module contains articles about basic Java concurrency
- [Guide to AtomicMarkableReference](https://www.baeldung.com/java-atomicmarkablereference)
- [Why are Local Variables Thread-Safe in Java](https://www.baeldung.com/java-local-variables-thread-safe)
- [How to Stop Execution After a Certain Time in Java](https://www.baeldung.com/java-stop-execution-after-certain-time)
- [How to Handle InterruptedException in Java](https://www.baeldung.com/java-interrupted-exception)
- [How to Get the Number of Threads in a Java Process](https://www.baeldung.com/java-get-number-of-threads)
- [Set the Name of a Thread in Java](https://www.baeldung.com/java-set-thread-name)
- [[<-- Prev]](/core-java-modules/core-java-concurrency-basic)
- [[<-- Prev]](../core-java-concurrency-basic)[[Next -->]](../core-java-concurrency-basic-3)

View File

@ -0,0 +1,70 @@
package com.baeldung.concurrent.threads.name;
public class CustomThreadName {
public int currentNumber = 1;
public int N = 5;
public static void main(String[] args) {
CustomThreadName test = new CustomThreadName();
Thread oddThread = new Thread(() -> {
test.printOddNumber();
// Uncomment below to set thread name using setName() Method
// Thread.currentThread().setName("ODD");
}, "ODD");
// or Uncomment below to set thread name using setName() Method
// oddThread.setName("ODD");
Thread evenThread = new Thread(() -> {
test.printEvenNumber();
// Uncomment below to set thread name using setName() Method
// Thread.currentThread().setName("EVEN");
}, "EVEN");
// evenThread.setName("EVEN");
evenThread.start();
oddThread.start();
}
public void printEvenNumber() {
synchronized (this) {
while (currentNumber < N) {
while (currentNumber % 2 == 1) {
try {
wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(Thread.currentThread()
.getName() + " --> " + currentNumber);
currentNumber++;
notify();
}
}
}
public void printOddNumber() {
synchronized (this) {
while (currentNumber < N) {
while (currentNumber % 2 == 0) {
try {
wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(Thread.currentThread()
.getName() + " --> " + currentNumber);
currentNumber++;
notify();
}
}
}
}

View File

@ -7,12 +7,6 @@
</encoder>
</appender>
<logger name="org.springframework" level="WARN" />
<logger name="org.springframework.transaction" level="WARN" />
<!-- in order to debug some marshalling issues, this needs to be TRACE -->
<logger name="org.springframework.web.servlet.mvc" level="WARN" />
<root level="INFO">
<appender-ref ref="STDOUT" />
</root>

View File

@ -0,0 +1,8 @@
## Core Java Concurrency Basic
This module contains articles about basic Java concurrency.
### Relevant Articles:
- [How to Handle InterruptedException in Java](https://www.baeldung.com/java-interrupted-exception)
- [[<-- Prev]](../core-java-concurrency-basic-2)

View File

@ -0,0 +1,27 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<artifactId>core-java-concurrency-basic-3</artifactId>
<version>0.1.0-SNAPSHOT</version>
<name>core-java-concurrency-basic-3</name>
<packaging>jar</packaging>
<parent>
<groupId>com.baeldung.core-java-modules</groupId>
<artifactId>core-java-modules</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<build>
<finalName>core-java-concurrency-basic-3</finalName>
<resources>
<resource>
<directory>src/main/resources</directory>
<filtering>true</filtering>
</resource>
</resources>
</build>
</project>

View File

@ -0,0 +1,13 @@
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
</pattern>
</encoder>
</appender>
<root level="INFO">
<appender-ref ref="STDOUT" />
</root>
</configuration>

View File

@ -1,7 +1,7 @@
package com.baeldung.concurrent.interrupt;
import static org.junit.Assert.assertTrue;
import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.junit.jupiter.api.Assertions.assertTrue;
import org.junit.jupiter.api.Test;
@ -9,23 +9,23 @@ public class InterruptExampleUnitTest {
@Test
public void whenPropagateException_thenThrowsInterruptedException() {
assertThrows(InterruptedException.class, () -> InterruptExample.propagateException());
assertThrows(InterruptedException.class, InterruptExample::propagateException);
}
@Test
public void whenRestoreTheState_thenReturnsTrue() {
assertTrue(InterruptExample.restoreTheState());
}
@Test
public void whenThrowCustomException_thenContainsExpectedMessage() {
Exception exception = assertThrows(CustomInterruptedException.class, () -> InterruptExample.throwCustomException());
Exception exception = assertThrows(CustomInterruptedException.class, InterruptExample::throwCustomException);
String expectedMessage = "This thread was interrupted";
String actualMessage = exception.getMessage();
assertTrue(actualMessage.contains(expectedMessage));
}
@Test
public void whenHandleWithCustomException_thenReturnsTrue() throws CustomInterruptedException{
assertTrue(InterruptExample.handleWithCustomException());

View File

@ -2,4 +2,5 @@
- [Introduction to Lock Striping](https://www.baeldung.com/java-lock-stripping)
- [Guide to the Java TransferQueue](http://www.baeldung.com/java-transfer-queue)
- [Java Concurrent HashSet Equivalent to ConcurrentHashMap](https://www.baeldung.com/java-concurrent-hashset-concurrenthashmap)
- [[<-- Prev]](/core-java-modules/core-java-concurrency-collections)

View File

@ -25,7 +25,6 @@
<artifactId>commons-lang3</artifactId>
<version>${commons-lang3.version}</version>
</dependency>
<dependency>
<groupId>com.darwinsys</groupId>
<artifactId>hirondelle-date4j</artifactId>

View File

@ -7,7 +7,12 @@ import static org.junit.jupiter.api.Assertions.assertTrue;
import org.junit.jupiter.api.Test;
public class IllegalMonitorStateExceptionUnitTest {
/**
* Needs to be run manually in order to demonstrate the IllegalMonitorStateException scenarios.
*
* There are some intermittent test failures in Jenkins that require further investigation.
*/
public class IllegalMonitorStateExceptionManualTest {
@Test
void whenSyncSenderAndSyncReceiverAreUsed_thenIllegalMonitorExceptionShouldNotBeThrown() throws InterruptedException {

View File

@ -0,0 +1,4 @@
### Relevant Articles:
- [Java ArrayIndexOutOfBoundsException](https://www.baeldung.com/java-arrayindexoutofboundsexception)
- [Java Missing Return Statement](https://www.baeldung.com/java-missing-return-statement)

View File

@ -0,0 +1,47 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.baeldung.exceptions</groupId>
<artifactId>core-java-exceptions-4</artifactId>
<version>0.1.0-SNAPSHOT</version>
<name>core-java-exceptions-4</name>
<packaging>jar</packaging>
<parent>
<groupId>com.baeldung.core-java-modules</groupId>
<artifactId>core-java-modules</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<dependencies>
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
<version>${h2.version}</version>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.8.1</version>
<configuration>
<compilerArgs>
<!-- Comment the arg below to print complete stack trace information -->
<!-- <arg>-g:none</arg>-->
</compilerArgs>
</configuration>
</plugin>
</plugins>
</build>
<properties>
<h2.version>1.4.191</h2.version>
</properties>
</project>

View File

@ -0,0 +1,31 @@
package com.baeldung.exception.arrayindexoutofbounds;
import java.util.Arrays;
import java.util.List;
public class ArrayIndexOutOfBoundsExceptionDemo {
public static void main(String[] args) {
int[] numbers = new int[] { 1, 2, 3, 4, 5 };
getArrayElementAtIndex(numbers, 5);
getListElementAtIndex(5);
addArrayElementsUsingLoop(numbers);
}
public static void addArrayElementsUsingLoop(int[] numbers) {
int sum = 0;
for (int i = 0; i <= numbers.length; i++) {
sum += numbers[i];
}
}
public static int getListElementAtIndex(int index) {
List<Integer> numbersList = Arrays.asList(1, 2, 3, 4, 5);
return numbersList.get(index);
}
public static int getArrayElementAtIndex(int[] numbers, int index) {
return numbers[index];
}
}

Some files were not shown because too many files have changed in this diff Show More