001package conexp.fx.core.math; 002 003/* 004 * #%L 005 * Concept Explorer FX 006 * %% 007 * Copyright (C) 2010 - 2023 Francesco Kriegel 008 * %% 009 * This program is free software: you can redistribute it and/or modify 010 * it under the terms of the GNU General Public License as 011 * published by the Free Software Foundation, either version 3 of the 012 * License, or (at your option) any later version. 013 * 014 * This program is distributed in the hope that it will be useful, 015 * but WITHOUT ANY WARRANTY; without even the implied warranty of 016 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 017 * GNU General Public License for more details. 018 * 019 * You should have received a copy of the GNU General Public 020 * License along with this program. If not, see 021 * <http://www.gnu.org/licenses/gpl-3.0.html>. 022 * #L% 023 */ 024 025import com.google.common.base.Function; 026 027public abstract class GuavaIsomorphism<A, B> implements Function<A, B> { 028 029 public static final <A> GuavaIsomorphism<A, A> identity() { 030 return new GuavaIsomorphism<A, A>() { 031 032 @Override 033 public A apply(A a) { 034 return a; 035 } 036 037 @Override 038 public A invert(A a) { 039 return a; 040 } 041 }; 042 } 043 044 public static final <A, B> GuavaIsomorphism<A, B> create(final Function<A, B> function, final Function<B, A> inverse) { 045 return new GuavaIsomorphism<A, B>() { 046 047 @Override 048 public final B apply(final A a) { 049 return function.apply(a); 050 } 051 052 @Override 053 public final A invert(final B b) { 054 return inverse.apply(b); 055 } 056 057 @Override 058 public Function<A, B> function() { 059 return function; 060 } 061 062 @Override 063 public Function<B, A> inverse() { 064 return inverse; 065 } 066 }; 067 } 068 069 public static final <A, B> GuavaIsomorphism<B, A> invert(final GuavaIsomorphism<A, B> isomorphism) { 070 return new GuavaIsomorphism<B, A>() { 071 072 @Override 073 public final A apply(final B b) { 074 return isomorphism.invert(b); 075 } 076 077 @Override 078 public final B invert(final A a) { 079 return isomorphism.apply(a); 080 } 081 082 @Override 083 public Function<B, A> function() { 084 return isomorphism.inverse(); 085 } 086 087 @Override 088 public Function<A, B> inverse() { 089 return isomorphism.function(); 090 } 091 }; 092 } 093 094 public static final <A, B, C> GuavaIsomorphism<A, C> 095 compose(final GuavaIsomorphism<A, B> isomorphism1, final GuavaIsomorphism<B, C> isomorphism2) { 096 return new GuavaIsomorphism<A, C>() { 097 098 @Override 099 public final C apply(final A a) { 100 return isomorphism2.apply(isomorphism1.apply(a)); 101 } 102 103 @Override 104 public final A invert(final C c) { 105 return isomorphism1.invert(isomorphism2.invert(c)); 106 } 107 }; 108 } 109 110 public A invert(B b) { 111 throw new RuntimeException(); 112 } 113 114 public Function<A, B> function() { 115 return this; 116 } 117 118 public Function<B, A> inverse() { 119 return new Function<B, A>() { 120 121 @Override 122 public final A apply(final B b) { 123 return GuavaIsomorphism.this.invert(b); 124 } 125 }; 126 } 127 128 public final java.util.function.Function<A, B> toJavaFunction() { 129 return a -> apply(a); 130 } 131 132 public final java.util.function.Function<B, A> inverseToJavaFunction() { 133 return b -> invert(b); 134 } 135}