From 3e3325ad28c12a43c5fcd61f5d53eaf2e7e75ffd Mon Sep 17 00:00:00 2001 From: Marc Pfetsch Date: Mon, 18 Dec 2023 11:49:23 +0100 Subject: [PATCH] allow to skip '*' between number and variable when parsing expr - handle the no-asterisk case as if there was one if number if followed by '<' --- CHANGELOG | 3 +++ src/scip/scip_expr.c | 21 +++++++++++++++------ src/scip/scip_expr.h | 2 +- 3 files changed, 19 insertions(+), 7 deletions(-) diff --git a/CHANGELOG b/CHANGELOG index 1bcfe521cb..05ab1e084c 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -38,6 +38,9 @@ Features - added a new separator sepa_lagromory to generate Lagromory cuts in a relax-and-cut framework, i.e., GMI cuts generated at different bases that are explored in the process of solving the Lagrangian dual problem at a node. This separator is OFF by default. +- when parsing nonlinear constraints from CIP files, the * after the number in a term is now optional if followed by a variable, + i.e., instead of 3**, now also 3* can be read, but 3 is not supported; + this allows to read some CIP files that were written with SCIP < 8 Performance improvements ------------------------ diff --git a/src/scip/scip_expr.c b/src/scip/scip_expr.c index 1f3a8aa824..461dd214ec 100644 --- a/src/scip/scip_expr.c +++ b/src/scip/scip_expr.c @@ -574,19 +574,28 @@ SCIP_RETCODE parseExpr( { SCIP_CALL( SCIPskipSpace((char**)newpos) ); - if( **newpos != '*' ) + if( **newpos == '<' ) { - /* no '*', so fall back to parsing term after sign */ - coef = (*expr == '+') ? 1.0 : -1.0; - ++expr; + /* found variable name ('*' is considered optional); + * keep coefficient in coef and continue parsing term after coefficient + */ + expr = *newpos; + + SCIP_CALL( SCIPskipSpace((char**)&expr) ); } - else + else if( **newpos == '*' ) { /* keep coefficient in coef and continue parsing term after coefficient */ expr = (*newpos)+1; SCIP_CALL( SCIPskipSpace((char**)&expr) ); } + else + { + /* term consists of single value; let parseTerm() below parse it */ + coef = (*expr == '+') ? 1.0 : -1.0; + ++expr; + } } else { @@ -1358,7 +1367,7 @@ SCIP_RETCODE SCIPcopyExpr( * * The actual definition: *
- * Expression -> ["+" | "-"] Term { ("+" | "-" | "number *") ] Term }
+ * Expression -> ["+" | "-"] Term { [ ("+" | "-" | "number *") Term | ("number" ) ] }
  * Term       -> Factor { ("*" | "/" ) Factor }
  * Factor     -> Base [ "^" "number" | "^(" "number" ")" ]
  * Base       -> "number" | "" | "(" Expression ")" | Op "(" OpExpression ")
diff --git a/src/scip/scip_expr.h b/src/scip/scip_expr.h
index 43bef970ca..93fdc0ed86 100644
--- a/src/scip/scip_expr.h
+++ b/src/scip/scip_expr.h
@@ -277,7 +277,7 @@ SCIP_RETCODE SCIPcopyExpr(
  *
  * The actual definition:
  * 
- * Expression -> ["+" | "-"] Term { ("+" | "-" | "number *") ] Term }
+ * Expression -> ["+" | "-"] Term { [ ("+" | "-" | "number *") Term | ("number" ) ] }
  * Term       -> Factor { ("*" | "/" ) Factor }
  * Factor     -> Base [ "^" "number" | "^(" "number" ")" ]
  * Base       -> "number" | "" | "(" Expression ")" | Op "(" OpExpression ")