Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Add regexp_substr function for returning matched part of string again…
…st regex
  • Loading branch information
nyalldawson committed May 12, 2013
1 parent c07b2cc commit a85b0bc
Show file tree
Hide file tree
Showing 3 changed files with 43 additions and 1 deletion.
14 changes: 14 additions & 0 deletions resources/function_help/regexp_substr-en_US
@@ -0,0 +1,14 @@
<h3>regexp_substr() function</h3>
Returns the portion of a string which matches a supplied regular expression.

<p><h4>Syntax</h4>
regexp_substr(<i>string,regex</i>)</p>

<p><h4>Arguments</h4>
<!-- List args for functions here-->
<i> string</i> &rarr; is string. The input string.<br>
<i> regex</i> &rarr; is string. The regular expression to match against. Backslash characters must be double escaped (eg "\\s" to match a white space character).<br>

<p><h4>Example</h4>
<!-- Show example of function.-->
regexp_substr('abc123','(\\d+)') &rarr; '123'</p>
28 changes: 27 additions & 1 deletion src/core/qgsexpression.cpp
Expand Up @@ -521,6 +521,31 @@ static QVariant fcnRegexpMatch( const QVariantList& values, QgsFeature* , QgsExp
return QVariant( str.contains( re ) ? 1 : 0 );
}

static QVariant fcnRegexpSubstr( const QVariantList& values, QgsFeature* , QgsExpression* parent )
{
QString str = getStringValue( values.at( 0 ), parent );
QString regexp = getStringValue( values.at( 1 ), parent );

QRegExp re( regexp );
if ( !re.isValid() )
{
parent->setEvalErrorString( QObject::tr( "Invalid regular expression '%1': %2" ).arg( regexp ).arg( re.errorString() ) );
return QVariant();
}

// extract substring
re.indexIn( str );
if ( re.captureCount() > 0 )
{
// return first capture
return QVariant( re.capturedTexts()[0] );
}
else
{
return QVariant( "" );
}
}

static QVariant fcnSubstr( const QVariantList& values, QgsFeature* , QgsExpression* parent )
{
QString str = getStringValue( values.at( 0 ), parent );
Expand Down Expand Up @@ -1233,7 +1258,7 @@ const QStringList &QgsExpression::BuiltinFunctions()
<< "coalesce" << "regexp_match" << "$now" << "age" << "year"
<< "month" << "week" << "day" << "hour"
<< "minute" << "second" << "lower" << "upper"
<< "title" << "length" << "replace" << "regexp_replace"
<< "title" << "length" << "replace" << "regexp_replace" << "regexp_substr"
<< "substr" << "concat" << "strpos" << "left"
<< "right" << "rpad" << "lpad"
<< "format_number" << "format_date"
Expand Down Expand Up @@ -1294,6 +1319,7 @@ const QList<QgsExpression::Function*> &QgsExpression::Functions()
<< new StaticFunction( "length", 1, fcnLength, QObject::tr( "String" ) )
<< new StaticFunction( "replace", 3, fcnReplace, QObject::tr( "String" ) )
<< new StaticFunction( "regexp_replace", 3, fcnRegexpReplace, QObject::tr( "String" ) )
<< new StaticFunction( "regexp_substr", 2, fcnRegexpSubstr, QObject::tr( "String" ) )
<< new StaticFunction( "substr", 3, fcnSubstr, QObject::tr( "String" ) )
<< new StaticFunction( "concat", -1, fcnConcat, QObject::tr( "String" ) )
<< new StaticFunction( "strpos", 2, fcnStrpos, QObject::tr( "String" ) )
Expand Down
2 changes: 2 additions & 0 deletions tests/src/core/testqgsexpression.cpp
Expand Up @@ -274,6 +274,8 @@ class TestQgsExpression: public QObject
QTest::newRow( "regexp_replace invalid" ) << "regexp_replace('HeLLo','[[[', '-')" << true << QVariant();
QTest::newRow( "substr" ) << "substr('HeLLo', 3,2)" << false << QVariant( "LL" );
QTest::newRow( "substr outside" ) << "substr('HeLLo', -5,2)" << false << QVariant( "" );
QTest::newRow( "regexp_substr" ) << "regexp_substr('abc123','(\\\\d+)')" << false << QVariant( "123" );
QTest::newRow( "regexp_substr invalid" ) << "regexp_substr('abc123','([[[')" << true << QVariant();
QTest::newRow( "strpos" ) << "strpos('Hello World','World')" << false << QVariant( 6 );
QTest::newRow( "strpos outside" ) << "strpos('Hello World','blah')" << false << QVariant( -1 );
QTest::newRow( "left" ) << "left('Hello World',5)" << false << QVariant( "Hello" );
Expand Down

0 comments on commit a85b0bc

Please sign in to comment.