Multiple CONTAINS in WHERE Clause in Google Sheets Query

This tutorial explains how to specify multiple CONTAINS for partial matching strings in the WHERE clause in Google Sheets Query.

Besides aggregation, the QUERY function in Google Sheets showcases excellent capabilities for string matching. This feature significantly enhances the tool’s ability to perform advanced data filtering.

There are simple comparison operators and five complex string comparison operators to achieve that. The complex string comparison operators are CONTAINS, MATCHES, LIKE, STARTS WITH, and ENDS WITH.

Some of you may already be well aware of the use of CONTAINS and its counterpart, NOT CONTAINS, in Query. Here is an example:

Example 1 (Formula in cell D1): Extract all the ‘Product Codes’ that contain the string ‘ABC’.

=QUERY(A1:A, "SELECT * WHERE A CONTAINS 'ABC' ", 1) // case-sensitive
=QUERY(A1:A, "SELECT * WHERE LOWER(A) CONTAINS 'abc' ", 1) // case-insensitive
Query String Matching with CONTAINS and NOT CONTAINS

Example 2 (Formula in cell E1): Extract all the ‘Product Codes’ that do not contain ‘ABC’.

=QUERY(A1:A, "SELECT * WHERE NOT A CONTAINS 'ABC' ",1) // case-sensitive
=QUERY(A1:A, "SELECT * WHERE NOT LOWER(A) CONTAINS 'abc' ", 1) // case-insensitive

The purpose of using multiple CONTAINS in the Query WHERE clause is to perform multiple substring matches. Let me address that issue, which is the main topic of this post.

Note: You can enter the string to match in a cell, for example, in cell F2, and refer to that cell as follows: '"&F2&"'. This means you should replace 'ABC' (or 'abc') with '"&F2&"' in the above formulas.

Multiple CONTAINS in the QUERY Function and Practicality Issues

Of course, we can use multiple CONTAINS in the QUERY function WHERE clause for multiple substring matches. First, let’s see how to do that.

We can use the following QUERY formula to filter column A where the rows partially match ‘ABC’ or ‘XYZ’ (case-sensitive):

=QUERY(A1:A, "SELECT * WHERE A CONTAINS 'ABC' or A CONTAINS 'XYZ'", 1)

This works wonderfully. However, the issue arises when the number of strings to match increases, requiring many ‘CONTAINS’ and OR logical operators to separate each CONTAINS. This makes the formula longer and more difficult to manage.

So, how do we properly use multiple CONTAINS in the QUERY function WHERE clause?

Let’s find out.

MATCHES: The Alternative to Multiple CONTAINS in Query

Before we proceed with multiple substring matches, let’s replace our D1 and E1 formulas first. We will replace CONTAINS in those formulas with MATCHES.

MATCHES in WHERE Clause (Example Formula in cell D1):

=QUERY(A1:A, "SELECT * WHERE A MATCHES '.*ABC.*' ",1)

NOT MATCHES in WHERE Clause (Example Formula in cell E1):

=QUERY(A1:A,"SELECT * WHERE NOT A MATCHES '.*ABC.*' ",1)

When replacing CONTAINS with MATCHES, ensure to include .* around the criterion. If you want to refer to a cell, for example, cell F2, where you have entered ABC, replace '.*ABC.*' with '.*"&F2&".*'.

Examples of Multiple Partial Matches of Strings

In the earlier examples, I extracted the ‘Product Codes’ that contain/don’t contain the substring ‘ABC’. Now I am going to demonstrate multiple substring matches/mismatches in Query formulas.

See the following formulas:

Formula in D1:

=QUERY(A1:A,"SELECT * WHERE A MATCHES '.*ABC.*|.*DJ.*' ", 1)

Formula in E1:

=QUERY(A1:A, "SELECT * WHERE NOT A MATCHES '.*ABC.*|.*DJ.*' ", 1)
Example of Multiple CONTAINS in WHERE Clause in Query

When replacing a single criterion CONTAINS with multiple criteria MATCHES, in addition to the .* around the criterion, include a | separator between the strings. This allows us to include several partial matching as well as non-matching criteria in a single Query.

Yes! MATCHES-based string matching is my answer to how to use multiple CONTAINS in the WHERE clause in Google Sheets Query.

Specifying a Criteria Range in MATCHES in Query

Assume the conditions (substrings) to match are entered in B2:B3, where ABC is in B2 and DJ is in B3. Then you can replace '.*ABC.*|.*DJ.*' (regular expression) in the formula with the following code:

ArrayFormula("'"&TEXTJOIN(".*|", TRUE, ".*"&TOCOL(B2:B3, 1))&".*'")

Just replacing that regular expression won’t suffice. Use the formula as follows:

=QUERY(A1:A,"SELECT * WHERE A MATCHES "&ArrayFormula("'"&TEXTJOIN(".*|", TRUE, ".*"&TOCOL(B2:B3, 1))&".*'")&" ", 1)

In the above code, the TOCOL function ensures that blank cells, if any, in the criteria range are removed, and the TEXTJOIN function joins the values placing a .*| delimiter in between.

This is the dynamic way to use multiple CONTAINS in the WHERE clause in Google Sheets Query using MATCHES substring match.

Before concluding, here’s one bonus tip. Do you know how to use CONTAINS and NOT CONTAINS in a single Query?

CONTAINS and NOT CONTAINS in a Single Query Formula

Here, for two criteria partial match, one containing and the other not containing, you can use CONTAINS in the WHERE clause. For single as well as multiple conditions (matches/mismatches), use MATCHES.

Single Condition CONTAINS and NOT CONTAINS:

=QUERY(A1:A, "SELECT * WHERE A CONTAINS 'ABC' AND NOT A CONTAINS 101", 1)

Multiple MATCHES and NOT MATCHES (Multiple CONTAINS and NOT CONTAINS):

=QUERY(A1:A, "SELECT * WHERE A MATCHES '.*AB.*|.*DJ.*' AND NOT A MATCHES '.*101.*|.*102.*' ", 1)

Resources

Prashanth KV
Prashanth KV
Your Trusted Google Sheets and Excel Guide Prashanth KV brings a wealth of experience in Google Sheets and Excel, cultivated through years of work with multinational corporations in Mumbai and Dubai. As a recognized Google Product Expert in Docs Editors, Prashanth shares his expertise through insightful blogging since 2012. Explore his blog for practical tips and guidance on maximizing your spreadsheet skills.

Calculate Weighted Average in Pivot Table in Google Sheets

You can calculate a weighted average in a Pivot Table using a custom formula...

Summarize Data and Keep the Last Record in Google Sheets

In Google Sheets, we can summarize data (like sum, average, min, max, count) using...

How to Retrieve the Last Record in Each Group in Excel

As part of data analysis, you may need to retrieve the last record from...

Filter Data with Multi-Select Drop-Downs in Google Sheets

If you've started using multi-select drop-downs in Google Sheets, you may encounter challenges when...

More like this

Calculate Weighted Average in Pivot Table in Google Sheets

You can calculate a weighted average in a Pivot Table using a custom formula...

Summarize Data and Keep the Last Record in Google Sheets

In Google Sheets, we can summarize data (like sum, average, min, max, count) using...

Filter Data with Multi-Select Drop-Downs in Google Sheets

If you've started using multi-select drop-downs in Google Sheets, you may encounter challenges when...

11 COMMENTS

  1. I am hoping you can help. I am trying to populate data based on two separate requests. Column E has school grades (EE3, EE4, Kindergarten, 1st grade, etc.), and Column H has testing requested (speech, cognition, dyslexia, etc.). I need two kinds of data to populate into one spreadsheet:

    1. If the school grade is not EE3 or EE4, no matter the testing requested.
    2. If the school grade is EE3 or EE4 and they are only requesting speech.

    I can get the first populated, but I cannot seem to figure out how to add the second request of “if/then” to the same spreadsheet.

    • Hi Ashley Morland,

      You can try the following QUERY formula:

      =QUERY({'Sample Sheet'!E:H},"Select * where (Col1 matches 'EE3|EE4' and Col4='speech') or
      (not(Col1) matches 'EE3|EE4' and Col1 is not null)")

      You need to make two changes in this formula:

      1. Replace Sample Sheet with the actual sheet name containing the source data.
      2. Replace commas with semicolons as per your LOCALE settings.

  2. Hello! This solution helped me in my report.

    The only thing I can’t figure out with the formula is instead of B2:B3, how to use a larger range, for example, B2:B20, and it has only five values.

    How do you factor in the blank cells?

    Looking forward to your answer.

  3. The array formula you used to match conditions as a range is genius. Thank you so much for sharing. I haven’t seen this solution anywhere else.

LEAVE A REPLY

Please enter your comment!
Please enter your name here

This site uses Akismet to reduce spam. Learn how your comment data is processed.