[jOOQ/jOOQ#9790] Add internal functional interfaces F0, F1, F2

This commit is contained in:
Lukas Eder 2020-02-04 16:32:28 +01:00
parent 2708d2e0e8
commit d67f96aa5b
9 changed files with 46 additions and 117 deletions

View File

@ -106,7 +106,7 @@ final class CursorImpl<R extends Record> extends AbstractCursor<R> implements Cu
private final boolean keepStatement;
private final boolean autoclosing;
private final int maxRows;
private final RecordFactory<? extends R> factory;
private final F0<? extends R> factory;
private boolean isClosed;
private transient CursorResultSet rs;
@ -1610,7 +1610,7 @@ final class CursorImpl<R extends Record> extends AbstractCursor<R> implements Cu
rs.updateRow();
}
record = Tools.newRecord(true, (RecordFactory<AbstractRecord>) factory, ((DefaultExecuteContext) ctx).originalConfiguration())
record = Tools.newRecord(true, (F0<AbstractRecord>) factory, ((DefaultExecuteContext) ctx).originalConfiguration())
.operate(new CursorRecordInitialiser(fields.fields, 0));
rows++;

View File

@ -48,7 +48,6 @@ import org.jooq.RecordMapper;
import org.jooq.RecordMapperProvider;
import org.jooq.RecordType;
import org.jooq.impl.Tools.Cache;
import org.jooq.impl.Tools.Cache.CachedOperation;
/**
* A default {@link RecordMapperProvider} implementation, providing a
@ -81,9 +80,9 @@ public class DefaultRecordMapperProvider implements RecordMapperProvider, Serial
@Override
public final <R extends Record, E> RecordMapper<R, E> provide(final RecordType<R> rowType, final Class<? extends E> type) {
if (configuration != null && TRUE.equals(configuration.settings().isCacheRecordMappers()))
return Cache.run(configuration, new CachedOperation<RecordMapper<R, E>>() {
return Cache.run(configuration, new F0<RecordMapper<R, E>>() {
@Override
public RecordMapper<R, E> call() {
public RecordMapper<R, E> apply() {
return new DefaultRecordMapper<>(rowType, type, configuration);
}
}, DATA_CACHE_RECORD_MAPPERS, Cache.key(rowType, type));

View File

@ -38,6 +38,13 @@
package org.jooq.impl;
@FunctionalInterface
interface F0<R> {
R apply();
}
@FunctionalInterface
interface F1<T1, R> {

View File

@ -313,9 +313,9 @@ final class LoaderImpl<R extends Record> implements
@Override
public final LoaderRowsStep<R> loadRecords(Iterator<? extends Record> records) {
return loadArrays(new MappingIterator<Record, Object[]>(records, new MappingIterator.Function<Record, Object[]>() {
return loadArrays(new MappingIterator<Record, Object[]>(records, new F1<Record, Object[]>() {
@Override
public final Object[] map(Record value) {
public final Object[] apply(Record value) {
if (value == null)
return null;

View File

@ -44,10 +44,10 @@ import java.util.Iterator;
*/
final class MappingIterator<T, U> implements Iterator<U> {
final Iterator<? extends T> delegate;
final Function<? super T, ? extends U> mapper;
final Iterator<? extends T> delegate;
final F1<? super T, ? extends U> mapper;
MappingIterator(Iterator<? extends T> delegate, Function<? super T, ? extends U> mapper) {
MappingIterator(Iterator<? extends T> delegate, F1<? super T, ? extends U> mapper) {
this.delegate = delegate;
this.mapper = mapper;
}
@ -59,15 +59,11 @@ final class MappingIterator<T, U> implements Iterator<U> {
@Override
public U next() {
return mapper.map(delegate.next());
return mapper.apply(delegate.next());
}
@Override
public void remove() {
delegate.remove();
}
interface Function<T, U> {
U map(T value);
}
}

View File

@ -1,55 +0,0 @@
/*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* Other licenses:
* -----------------------------------------------------------------------------
* Commercial licenses for this work are available. These replace the above
* ASL 2.0 and offer limited warranties, support, maintenance, and commercial
* database integrations.
*
* For more information, please visit: http://www.jooq.org/licenses
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*/
package org.jooq.impl;
import org.jooq.Record;
/**
* @author Lukas Eder
* @author Arnaud Roger
*/
@FunctionalInterface
interface RecordFactory<R extends Record> {
/**
* Create a new record with a given row type.
*/
R newInstance();
}

View File

@ -191,7 +191,6 @@ import org.jooq.WindowDefinition;
import org.jooq.exception.DataAccessException;
import org.jooq.impl.Tools.BooleanDataKey;
import org.jooq.impl.Tools.DataKey;
import org.jooq.impl.Transform.Transformer;
import org.jooq.tools.JooqLogger;
import org.jooq.tools.StringUtils;

View File

@ -264,7 +264,6 @@ import org.jooq.exception.MappingException;
import org.jooq.exception.NoDataFoundException;
import org.jooq.exception.TooManyRowsException;
import org.jooq.impl.ResultsImpl.ResultOrRowsImpl;
import org.jooq.impl.Tools.Cache.CachedOperation;
import org.jooq.tools.Ints;
import org.jooq.tools.JooqLogger;
import org.jooq.tools.StringUtils;
@ -858,9 +857,9 @@ final class Tools {
/**
* Create a new record.
*/
static final <R extends Record> RecordDelegate<R> newRecord(boolean fetched, RecordFactory<R> factory, Configuration configuration) {
static final <R extends Record> RecordDelegate<R> newRecord(boolean fetched, F0<R> factory, Configuration configuration) {
try {
R record = factory.newInstance();
R record = factory.apply();
// [#3300] Records that were fetched from the database
if (record instanceof AbstractRecord)
@ -877,15 +876,15 @@ final class Tools {
* Create a new record factory.
*/
@SuppressWarnings({ "unchecked", "rawtypes" })
static final <R extends Record> RecordFactory<R> recordFactory(final Class<R> type, final Field<?>[] fields) {
static final <R extends Record> F0<R> recordFactory(final Class<R> type, final Field<?>[] fields) {
// An ad-hoc type resulting from a JOIN or arbitrary SELECT
if (type == RecordImpl.class || type == Record.class) {
final RowImpl row = new RowImpl(fields);
return new RecordFactory<R>() {
return new F0<R>() {
@Override
public R newInstance() {
public R apply() {
return (R) new RecordImpl(row);
}
};
@ -898,9 +897,9 @@ final class Tools {
// [#919] Allow for accessing non-public constructors
final Constructor<R> constructor = Reflect.accessible(type.getDeclaredConstructor());
return new RecordFactory<R>() {
return new F0<R>() {
@Override
public R newInstance() {
public R apply() {
try {
return constructor.newInstance();
}
@ -3161,29 +3160,17 @@ final class Tools {
static class Cache {
/**
* A callback wrapping expensive operations.
*/
static interface CachedOperation<V> {
/**
* An expensive operation.
*/
V call();
}
/**
* Run a {@link CachedOperation} in the context of a
* {@link Configuration}.
* Run a cached operation in the context of a {@link Configuration}.
*
* @param configuration The configuration that may cache the outcome of
* the {@link CachedOperation}.
* the cached operation.
* @param operation The expensive operation.
* @param type The cache type to be used.
* @param keys The cache keys.
* @return The cached value or the outcome of the cached operation.
*/
@SuppressWarnings("unchecked")
static final <V> V run(Configuration configuration, CachedOperation<V> operation, DataCacheKey type, Object key) {
static final <V> V run(Configuration configuration, F0<V> operation, DataCacheKey type, Object key) {
// If no configuration is provided take the default configuration that loads the default Settings
if (configuration == null)
@ -3191,7 +3178,7 @@ final class Tools {
// Shortcut caching when the relevant Settings flag isn't set.
if (!reflectionCaching(configuration.settings()))
return operation.call();
return operation.apply();
Map<Object, Object> cache = (Map<Object, Object>) configuration.data(type);
if (cache == null) {
@ -3211,7 +3198,7 @@ final class Tools {
result = cache.get(key);
if (result == null) {
result = operation.call();
result = operation.apply();
cache.put(key, result == null ? NULL : result);
}
}
@ -3407,10 +3394,10 @@ final class Tools {
* or methods
*/
static final boolean hasColumnAnnotations(final Configuration configuration, final Class<?> type) {
return Cache.run(configuration, new CachedOperation<Boolean>() {
return Cache.run(configuration, new F0<Boolean>() {
@Override
public Boolean call() {
public Boolean apply() {
if (!isJPAAvailable())
return false;
@ -3443,10 +3430,10 @@ final class Tools {
* Get all members annotated with a given column name
*/
static final List<java.lang.reflect.Field> getAnnotatedMembers(final Configuration configuration, final Class<?> type, final String name) {
return Cache.run(configuration, new CachedOperation<List<java.lang.reflect.Field>>() {
return Cache.run(configuration, new F0<List<java.lang.reflect.Field>>() {
@Override
public List<java.lang.reflect.Field> call() {
public List<java.lang.reflect.Field> apply() {
List<java.lang.reflect.Field> result = new ArrayList<>();
for (java.lang.reflect.Field member : getInstanceMembers(type)) {
@ -3484,10 +3471,10 @@ final class Tools {
* Get all members matching a given column name
*/
static final List<java.lang.reflect.Field> getMatchingMembers(final Configuration configuration, final Class<?> type, final String name) {
return Cache.run(configuration, new CachedOperation<List<java.lang.reflect.Field>>() {
return Cache.run(configuration, new F0<List<java.lang.reflect.Field>>() {
@Override
public List<java.lang.reflect.Field> call() {
public List<java.lang.reflect.Field> apply() {
List<java.lang.reflect.Field> result = new ArrayList<>();
// [#1942] Caching these values before the field-loop significantly
@ -3510,10 +3497,10 @@ final class Tools {
* Get all setter methods annotated with a given column name
*/
static final List<Method> getAnnotatedSetters(final Configuration configuration, final Class<?> type, final String name) {
return Cache.run(configuration, new CachedOperation<List<Method>>() {
return Cache.run(configuration, new F0<List<Method>>() {
@Override
public List<Method> call() {
public List<Method> apply() {
Set<SourceMethod> set = new LinkedHashSet<>();
for (Method method : getInstanceMethods(type)) {
@ -3561,10 +3548,10 @@ final class Tools {
* Get the first getter method annotated with a given column name
*/
static final Method getAnnotatedGetter(final Configuration configuration, final Class<?> type, final String name) {
return Cache.run(configuration, new CachedOperation<Method>() {
return Cache.run(configuration, new F0<Method>() {
@Override
public Method call() {
public Method apply() {
for (Method method : getInstanceMethods(type)) {
Column column = method.getAnnotation(Column.class);
@ -3612,10 +3599,10 @@ final class Tools {
* Get all setter methods matching a given column name
*/
static final List<Method> getMatchingSetters(final Configuration configuration, final Class<?> type, final String name) {
return Cache.run(configuration, new CachedOperation<List<Method>>() {
return Cache.run(configuration, new F0<List<Method>>() {
@Override
public List<Method> call() {
public List<Method> apply() {
// [#8460] Prevent duplicate methods in the call hierarchy
Set<SourceMethod> set = new LinkedHashSet<>();
@ -3650,10 +3637,10 @@ final class Tools {
* Get the first getter method matching a given column name
*/
static final Method getMatchingGetter(final Configuration configuration, final Class<?> type, final String name) {
return Cache.run(configuration, new CachedOperation<Method>() {
return Cache.run(configuration, new F0<Method>() {
@Override
public Method call() {
public Method apply() {
// [#1942] Caching these values before the method-loop significantly
// accerates POJO mapping
String camelCase = StringUtils.toCamelCase(name);

View File

@ -61,9 +61,9 @@ import org.jooq.QueryPart;
*/
final class Transform {
final Transformer<Field<?>> fieldTransformer;
final F1<Field<?>, Field<?>> fieldTransformer;
Transform(Transformer<Field<?>> fieldTransformer) {
Transform(F1<Field<?>, Field<?>> fieldTransformer) {
this.fieldTransformer = fieldTransformer;
}
@ -73,7 +73,7 @@ final class Transform {
else if (condition instanceof CombinedCondition)
return CombinedCondition.of(((CombinedCondition) condition).operator, transform(((CombinedCondition) condition).conditions));
else if (condition instanceof CompareCondition)
return new CompareCondition(fieldTransformer.transform(((CompareCondition) condition).field1), fieldTransformer.transform(((CompareCondition) condition).field2), ((CompareCondition) condition).comparator);
return new CompareCondition(fieldTransformer.apply(((CompareCondition) condition).field1), fieldTransformer.apply(((CompareCondition) condition).field2), ((CompareCondition) condition).comparator);
else
return condition;
}
@ -86,8 +86,4 @@ final class Transform {
return result;
}
interface Transformer<Q extends QueryPart> {
Q transform(Q queryPart);
}
}