Skip to content

Commit a52cb66

Browse files
author
Zihlu Wang
authored
Merge pull request #42 from OnixByte/release/1.6.5
v1.6.5
2 parents 635d4f7 + cc99b89 commit a52cb66

File tree

8 files changed

+286
-49
lines changed

8 files changed

+286
-49
lines changed

.github/workflows/github-packages-publish.yml

Lines changed: 7 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,9 @@
88
name: Publish Packages to GitHub Packages with Gradle
99

1010
on:
11-
push:
12-
branches:
13-
- main
11+
release:
12+
types:
13+
- published
1414

1515
jobs:
1616
build:
@@ -51,19 +51,17 @@ jobs:
5151
- name: Set up JDK 17
5252
uses: actions/setup-java@v4
5353
with:
54-
java-version: '17'
55-
distribution: 'corretto'
56-
server-id: github # Value of the distributionManagement/repository/id field of the pom.xml
57-
settings-path: ${{ github.workspace }} # location for the settings.xml file
54+
java-version: "17"
55+
distribution: "corretto"
5856

5957
- name: Setup Gradle
60-
uses: gradle/actions/setup-gradle@417ae3ccd767c252f5661f1ace9f835f9654f2b5 # v3.1.0
58+
uses: gradle/actions/setup-gradle@v4
6159

6260
- name: Grant Execution Authority to Gradlew
6361
run: chmod +x ./gradlew
6462

6563
- name: Build with Gradle
66-
run: ./gradlew build
64+
run: ./gradlew build -PartefactVersion=${{ github.event.release.tag_name }} # Overwrite artefactVersion
6765

6866
- name: Publish to Maven Central
6967
run: ./gradlew publish

devkit-utils/src/main/java/com/onixbyte/devkit/utils/BranchUtil.java

Lines changed: 16 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@
1717

1818
package com.onixbyte.devkit.utils;
1919

20-
import java.util.Arrays;
2120
import java.util.Objects;
2221
import java.util.function.BooleanSupplier;
2322
import java.util.function.Supplier;
@@ -89,62 +88,50 @@ private BranchUtil(boolean result) {
8988
* Creates a {@code BranchUtil} instance to evaluate a logical OR operation on the provided
9089
* boolean expressions.
9190
*
92-
* @param booleans the boolean expressions to be evaluated
93-
* @param <T> the type of the result to be handled by the methods
91+
* @param values the boolean expressions to be evaluated
92+
* @param <T> the type of the result to be handled by the methods
9493
* @return a {@code BranchUtil} instance representing the result of the logical OR operation
9594
*/
96-
public static <T> BranchUtil<T> or(Boolean... booleans) {
97-
var result = Arrays.stream(booleans)
98-
.filter(Objects::nonNull)
99-
.anyMatch(Boolean::booleanValue);
100-
return new BranchUtil<>(result);
95+
public static <T> BranchUtil<T> or(Boolean... values) {
96+
return new BranchUtil<>(BoolUtil.or(values));
10197
}
10298

10399
/**
104100
* Creates a {@code BranchUtil} instance to evaluate a logical AND operation on the provided
105101
* boolean expressions.
106102
*
107-
* @param booleans the boolean expressions to be evaluated
108-
* @param <T> the type of the result to be handled by the methods
103+
* @param values the boolean expressions to be evaluated
104+
* @param <T> the type of the result to be handled by the methods
109105
* @return a {@code BranchUtil} instance representing the result of the logical AND operation
110106
*/
111-
public static <T> BranchUtil<T> and(Boolean... booleans) {
112-
var result = Arrays.stream(booleans)
113-
.filter(Objects::nonNull)
114-
.allMatch(Boolean::booleanValue);
115-
return new BranchUtil<>(result);
107+
public static <T> BranchUtil<T> and(Boolean... values) {
108+
return new BranchUtil<>(BoolUtil.and(values));
116109
}
117110

118111
/**
119112
* Creates a {@code BranchUtil} instance to evaluate a logical OR operation on the provided
120113
* boolean suppliers.
121114
*
122-
* @param booleanSuppliers the boolean suppliers to be evaluated
123-
* @param <T> the type of the result to be handled by the methods
115+
* @param valueSuppliers the boolean suppliers to be evaluated
116+
* @param <T> the type of the result to be handled by the methods
124117
* @return a {@code BranchUtil} instance representing the result of the
125118
* logical OR operation
126119
*/
127-
public static <T> BranchUtil<T> or(BooleanSupplier... booleanSuppliers) {
128-
var result = Arrays.stream(booleanSuppliers)
129-
.filter(Objects::nonNull)
130-
.anyMatch(BooleanSupplier::getAsBoolean);
131-
return new BranchUtil<>(result);
120+
public static <T> BranchUtil<T> or(BooleanSupplier... valueSuppliers) {
121+
return new BranchUtil<>(BoolUtil.or(valueSuppliers));
132122
}
133123

134124
/**
135125
* Creates a {@code BranchUtil} instance to evaluate a logical AND operation on the provided
136126
* boolean suppliers.
137127
*
138-
* @param booleanSuppliers the boolean suppliers to be evaluated
139-
* @param <T> the type of the result to be handled by the methods
128+
* @param valueSuppliers the boolean suppliers to be evaluated
129+
* @param <T> the type of the result to be handled by the methods
140130
* @return a {@code BranchUtil} instance representing the result of the
141131
* logical AND operation
142132
*/
143-
public static <T> BranchUtil<T> and(BooleanSupplier... booleanSuppliers) {
144-
var result = Arrays.stream(booleanSuppliers)
145-
.filter(Objects::nonNull)
146-
.allMatch(BooleanSupplier::getAsBoolean);
147-
return new BranchUtil<>(result);
133+
public static <T> BranchUtil<T> and(BooleanSupplier... valueSuppliers) {
134+
return new BranchUtil<>(BoolUtil.and(valueSuppliers));
148135
}
149136

150137
/**

gradle.properties

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -15,18 +15,17 @@
1515
# limitations under the License.
1616
#
1717

18-
jacksonVersion=2.17.2
18+
jacksonVersion=2.18.0
1919
javaJwtVersion=4.4.0
20-
jjwtVersion=0.12.6
21-
junitVersion=5.10.2
22-
logbackVersion=1.5.4
23-
lombokVersion=1.18.30
24-
slf4jVersion=2.0.9
25-
springVersion=6.1.3
26-
springBootVersion=3.2.3
20+
junitVersion=5.11.2
21+
logbackVersion=1.5.10
22+
lombokVersion=1.18.34
23+
slf4jVersion=2.0.16
24+
springVersion=6.1.13
25+
springBootVersion=3.3.4
2726

2827
buildGroupId=com.onixbyte
29-
buildVersion=1.6.4
28+
buildVersion=1.6.5
3029
projectUrl=https://onixbyte.com/JDevKit
3130
projectGithubUrl=https://github.com/OnixByte/JDevKit
3231
licenseName=The Apache License, Version 2.0

num4j/build.gradle.kts

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
plugins {
2+
id("java")
3+
}
4+
5+
group = "com.onixbyte"
6+
version = "unspecified"
7+
8+
repositories {
9+
mavenCentral()
10+
}
11+
12+
dependencies {
13+
testImplementation(platform("org.junit:junit-bom:5.10.0"))
14+
testImplementation("org.junit.jupiter:junit-jupiter")
15+
}
16+
17+
tasks.test {
18+
useJUnitPlatform()
19+
}
Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515
* limitations under the License.
1616
*/
1717

18-
package com.onixbyte.devkit.utils;
18+
package com.onixbyte.nums;
1919

2020
import lombok.Getter;
2121

@@ -87,7 +87,7 @@
8787
*
8888
* @author sunzsh
8989
* @version 1.1.0
90-
* @see java.math.BigDecimal
90+
* @see BigDecimal
9191
* @since 1.0.0
9292
*/
9393
@Getter
Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
/*
2+
* Copyright (C) 2024 OnixByte.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
*
14+
* See the License for the specific language governing permissions and
15+
* limitations under the License.
16+
*/
17+
package com.onixbyte.nums;
18+
19+
import com.onixbyte.nums.model.QuartileBounds;
20+
21+
import java.util.List;
22+
23+
/**
24+
* A utility class that provides methods for calculating percentiles and interquartile range (IQR) bounds
25+
* for a dataset.
26+
* <p>
27+
* This class contains static methods to:
28+
* <ul>
29+
* <li>Calculate a specified percentile from a list of double values using linear interpolation.</li>
30+
* <li>Calculate interquartile bounds (Q1, Q3) and the corresponding lower and upper bounds,
31+
* which can be used to identify outliers in the dataset.</li>
32+
* </ul>
33+
* <p>
34+
* This class is final, meaning it cannot be subclassed, and it only contains static methods,
35+
* so instances of the class cannot be created.
36+
* </p>
37+
* <h2>Example usage:</h2>
38+
* <pre>
39+
* {@code
40+
* List<Double> data = Arrays.asList(1.0, 2.0, 3.0, 4.0, 5.0);
41+
* Double percentileValue = PercentileCalculator.calculatePercentile(data, 50.0); // Calculates median
42+
* QuartileBounds bounds = PercentileCalculator.calculatePercentileBounds(data); // Calculates IQR bounds
43+
* }
44+
* </pre>
45+
*
46+
* @author zihluwang
47+
* @version 1.6.5
48+
* @since 1.6.5
49+
*/
50+
public final class PercentileCalculator {
51+
52+
/**
53+
* Calculates the specified percentile from a list of values.
54+
* <p>
55+
* This method takes a list of double values and calculates the given percentile using linear interpolation between
56+
* the two closest ranks. The list is first sorted in ascending order, and the specified percentile is
57+
* then calculated.
58+
*
59+
* @param values a list of {@code Double} values from which the percentile is calculated.
60+
* @param percentile a {@code Double} representing the percentile to be calculated (e.g., 50.0 for the median)
61+
* @return a {@code Double} value representing the calculated percentile
62+
*/
63+
public static Double calculatePercentile(List<Double> values, Double percentile) {
64+
var sorted = values.stream().sorted().toList();
65+
if (sorted.isEmpty()) {
66+
throw new IllegalArgumentException("Unable to sort an empty list.");
67+
}
68+
69+
var rank = percentile / 100. * (sorted.size() - 1);
70+
var lowerIndex = (int) Math.floor(rank);
71+
var upperIndex = (int) Math.ceil(rank);
72+
var weight = rank - lowerIndex;
73+
74+
return sorted.get(lowerIndex) * (1 - weight) + sorted.get(upperIndex) * weight;
75+
}
76+
77+
/**
78+
* Calculates the interquartile range (IQR) and the corresponding lower and upper bounds
79+
* based on the first (Q1) and third (Q3) quartiles of a dataset.
80+
* <p>
81+
* This method takes a list of double values, calculates the first quartile (Q1),
82+
* the third quartile (Q3), and the interquartile range (IQR). Using the IQR, it computes
83+
* the lower and upper bounds, which can be used to detect outliers in the dataset.
84+
* The lower bound is defined as {@code Q1 - 1.5 * IQR}, and the upper bound is defined as
85+
* {@code Q3 + 1.5 * IQR}.
86+
*
87+
* @param data a list of {@code Double} values for which the quartile bounds will be calculated
88+
* @return a {@code QuartileBounds} object containing the calculated lower and upper bounds
89+
*/
90+
public static QuartileBounds calculatePercentileBounds(List<Double> data) {
91+
var sorted = data.stream().sorted().toList();
92+
var Q1 = calculatePercentile(sorted, 25.);
93+
var Q3 = calculatePercentile(sorted, 75.);
94+
95+
var IQR = Q3 - Q1;
96+
97+
var lowerBound = Q1 - 1.5 * IQR;
98+
var upperBound = Q3 + 1.5 * IQR;
99+
100+
return QuartileBounds.builder()
101+
.upperBound(upperBound)
102+
.lowerBound(lowerBound)
103+
.build();
104+
}
105+
106+
}

0 commit comments

Comments
 (0)