Skip to content

Commit 90adf82

Browse files
feat: CosineSimilarity Expression
- fixes #2005 Signed-off-by: Andreas Reichel <[email protected]>
1 parent d1373c5 commit 90adf82

File tree

8 files changed

+72
-0
lines changed

8 files changed

+72
-0
lines changed

src/main/java/net/sf/jsqlparser/expression/ExpressionVisitor.java

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
import net.sf.jsqlparser.expression.operators.relational.Between;
2828
import net.sf.jsqlparser.expression.operators.relational.ContainedBy;
2929
import net.sf.jsqlparser.expression.operators.relational.Contains;
30+
import net.sf.jsqlparser.expression.operators.relational.CosineSimilarity;
3031
import net.sf.jsqlparser.expression.operators.relational.DoubleAnd;
3132
import net.sf.jsqlparser.expression.operators.relational.EqualsTo;
3233
import net.sf.jsqlparser.expression.operators.relational.ExcludesExpression;
@@ -665,4 +666,6 @@ default void visit(PriorTo priorTo) {
665666
default void visit(Inverse inverse) {
666667
this.visit(inverse, null);
667668
}
669+
670+
<S> T visit(CosineSimilarity cosineSimilarity, S context);
668671
}

src/main/java/net/sf/jsqlparser/expression/ExpressionVisitorAdapter.java

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
import net.sf.jsqlparser.expression.operators.relational.Between;
2828
import net.sf.jsqlparser.expression.operators.relational.ContainedBy;
2929
import net.sf.jsqlparser.expression.operators.relational.Contains;
30+
import net.sf.jsqlparser.expression.operators.relational.CosineSimilarity;
3031
import net.sf.jsqlparser.expression.operators.relational.DoubleAnd;
3132
import net.sf.jsqlparser.expression.operators.relational.EqualsTo;
3233
import net.sf.jsqlparser.expression.operators.relational.ExcludesExpression;
@@ -792,4 +793,11 @@ public <S> T visit(Inverse inverse, S context) {
792793
return inverse.getExpression().accept(this, context);
793794
}
794795

796+
@Override
797+
public <S> T visit(CosineSimilarity cosineSimilarity, S context) {
798+
cosineSimilarity.getLeftExpression().accept(this, context);
799+
cosineSimilarity.getRightExpression().accept(this, context);
800+
return null;
801+
}
802+
795803
}
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
/*-
2+
* #%L
3+
* JSQLParser library
4+
* %%
5+
* Copyright (C) 2004 - 2022 JSQLParser
6+
* %%
7+
* Dual licensed under GNU LGPL 2.1 or Apache License 2.0
8+
* #L%
9+
*/
10+
package net.sf.jsqlparser.expression.operators.relational;
11+
12+
import net.sf.jsqlparser.expression.ExpressionVisitor;
13+
14+
public class CosineSimilarity extends ComparisonOperator {
15+
16+
public CosineSimilarity() {
17+
super("<=>");
18+
}
19+
20+
public CosineSimilarity(String operator) {
21+
super(operator);
22+
}
23+
24+
@Override
25+
public <T, S> T accept(ExpressionVisitor<T> expressionVisitor, S context) {
26+
return expressionVisitor.visit(this, context);
27+
}
28+
}

src/main/java/net/sf/jsqlparser/util/TablesNamesFinder.java

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,7 @@
8484
import net.sf.jsqlparser.expression.operators.relational.Between;
8585
import net.sf.jsqlparser.expression.operators.relational.ContainedBy;
8686
import net.sf.jsqlparser.expression.operators.relational.Contains;
87+
import net.sf.jsqlparser.expression.operators.relational.CosineSimilarity;
8788
import net.sf.jsqlparser.expression.operators.relational.DoubleAnd;
8889
import net.sf.jsqlparser.expression.operators.relational.EqualsTo;
8990
import net.sf.jsqlparser.expression.operators.relational.ExcludesExpression;
@@ -1624,6 +1625,13 @@ public <S> Void visit(Inverse inverse, S context) {
16241625
return null;
16251626
}
16261627

1628+
@Override
1629+
public <S> Void visit(CosineSimilarity cosineSimilarity, S context) {
1630+
cosineSimilarity.getLeftExpression().accept(this, context);
1631+
cosineSimilarity.getRightExpression().accept(this, context);
1632+
return null;
1633+
}
1634+
16271635
@Override
16281636
public <S> Void visit(VariableAssignment variableAssignment, S context) {
16291637
variableAssignment.getVariable().accept(this, context);

src/main/java/net/sf/jsqlparser/util/deparser/ExpressionDeParser.java

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,7 @@
8484
import net.sf.jsqlparser.expression.operators.relational.Between;
8585
import net.sf.jsqlparser.expression.operators.relational.ContainedBy;
8686
import net.sf.jsqlparser.expression.operators.relational.Contains;
87+
import net.sf.jsqlparser.expression.operators.relational.CosineSimilarity;
8788
import net.sf.jsqlparser.expression.operators.relational.DoubleAnd;
8889
import net.sf.jsqlparser.expression.operators.relational.EqualsTo;
8990
import net.sf.jsqlparser.expression.operators.relational.ExcludesExpression;
@@ -1742,4 +1743,11 @@ public <S> StringBuilder visit(PriorTo priorTo, S context) {
17421743
public <S> StringBuilder visit(Inverse inverse, S context) {
17431744
return buffer.append(inverse.toString());
17441745
}
1746+
1747+
@Override
1748+
public <S> StringBuilder visit(CosineSimilarity cosineSimilarity, S context) {
1749+
deparse(cosineSimilarity,
1750+
" " + cosineSimilarity.getStringExpression() + " ", context);
1751+
return buffer;
1752+
}
17451753
}

src/main/java/net/sf/jsqlparser/util/validation/validator/ExpressionValidator.java

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,7 @@
8585
import net.sf.jsqlparser.expression.operators.relational.Between;
8686
import net.sf.jsqlparser.expression.operators.relational.ContainedBy;
8787
import net.sf.jsqlparser.expression.operators.relational.Contains;
88+
import net.sf.jsqlparser.expression.operators.relational.CosineSimilarity;
8889
import net.sf.jsqlparser.expression.operators.relational.DoubleAnd;
8990
import net.sf.jsqlparser.expression.operators.relational.EqualsTo;
9091
import net.sf.jsqlparser.expression.operators.relational.ExcludesExpression;
@@ -1265,4 +1266,11 @@ public void visit(Inverse inverse) {
12651266
visit(inverse, null);
12661267
}
12671268

1269+
@Override
1270+
public <S> Void visit(CosineSimilarity cosineSimilarity, S context) {
1271+
cosineSimilarity.getLeftExpression().accept(this, context);
1272+
cosineSimilarity.getRightExpression().accept(this, context);
1273+
return null;
1274+
}
1275+
12681276
}

src/main/jjtree/net/sf/jsqlparser/parser/JSqlParserCC.jjt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4008,6 +4008,7 @@ Expression RegularCondition() #RegularCondition:
40084008
| "-#" { result = new JsonOperator("-#"); }
40094009
| "<->" { result = new GeometryDistance("<->"); }
40104010
| "<#>" { result = new GeometryDistance("<#>"); }
4011+
| "<=>" { result = new CosineSimilarity(); }
40114012
)
40124013

40134014
( LOOKAHEAD(2) <K_PRIOR> rightExpression=ComparisonItem() { oraclePrior = EqualsTo.ORACLE_PRIOR_END; }

src/test/java/net/sf/jsqlparser/expression/operators/relational/ComparisonOperatorTest.java

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,4 +35,12 @@ public void testContainedBy() throws JSQLParserException {
3535
TestUtils.assertSqlCanBeParsedAndDeparsed("SELECT * FROM foo WHERE a <& b");
3636
Assertions.assertInstanceOf(ContainedBy.class, CCJSqlParserUtil.parseExpression("a <& b"));
3737
}
38+
39+
@Test
40+
void testCosineSimilarity() throws JSQLParserException {
41+
TestUtils.assertSqlCanBeParsedAndDeparsed(
42+
"SELECT (embedding <=> '[3,1,2]') AS cosine_similarity FROM items;");
43+
Assertions.assertInstanceOf(CosineSimilarity.class,
44+
CCJSqlParserUtil.parseExpression("embedding <=> '[3,1,2]'"));
45+
}
3846
}

0 commit comments

Comments
 (0)