|  | --- | 
|  | title:  Creating Indexes on Map Fields ("Map Indexes") | 
|  | --- | 
|  |  | 
|  | <!-- | 
|  | Licensed to the Apache Software Foundation (ASF) under one or more | 
|  | contributor license agreements.  See the NOTICE file distributed with | 
|  | this work for additional information regarding copyright ownership. | 
|  | The ASF licenses this file to You under the Apache License, Version 2.0 | 
|  | (the "License"); you may not use this file except in compliance with | 
|  | the License.  You may obtain a copy of the License at | 
|  |  | 
|  | http://www.apache.org/licenses/LICENSE-2.0 | 
|  |  | 
|  | Unless required by applicable law or agreed to in writing, software | 
|  | distributed under the License is distributed on an "AS IS" BASIS, | 
|  | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | 
|  | See the License for the specific language governing permissions and | 
|  | limitations under the License. | 
|  | --> | 
|  |  | 
|  | To assist with the quick lookup of multiple values in a Map (or HashMap) type field, you can create an index (sometimes referred to as a "map index") on specific (or all) keys in that field. | 
|  |  | 
|  | For example, you could create a map index to support the following query: | 
|  |  | 
|  | ``` pre | 
|  | SELECT * FROM /users u WHERE u.name['first'] = 'John' OR u.name['last'] = 'Smith' | 
|  | ``` | 
|  |  | 
|  | The map index extends regular range indexes created on single key by maintaining indexes for other specified keys, or for all keys if `*` is used. The underlying structure of the map index can be thought of as a wrapper around all these indexes. | 
|  |  | 
|  | The following Java code samples provide examples of how to create a map index: | 
|  |  | 
|  | ``` pre | 
|  | QueryService qs = cache.getQueryService(); | 
|  |  | 
|  | //This will create indexes for for keys 'PVTL' and 'VMW' | 
|  | qs.createIndex("indexName", "p.positions['PVTL', 'VMW']", "/portfolio p"); | 
|  | ``` | 
|  |  | 
|  | ``` pre | 
|  | QueryService qs = cache.getQueryService(); | 
|  |  | 
|  | //This will create indexes for all keys | 
|  | qs.createIndex("indexName", "p.positions[*]", "/portfolio p"); | 
|  | ``` | 
|  |  | 
|  | In gfsh, the equivalents are: | 
|  |  | 
|  | ``` pre | 
|  | gfsh>create index --name="IndexName" --expression="p.positions['PVTL', 'VMW']" --region="/portfolio p" | 
|  |  | 
|  | gfsh>create index --name="IndexName" --expression="p.positions[*]" --region="/portfolio p" | 
|  | ``` | 
|  |  | 
|  | In order to create or query a map index, you must use the bracket notation to list the map field keys you wish to index or query. For example: `[*]`, `['keyX1','keyX2’]`. Note that using `p.pos.get('keyX1')` will not create or query the map index. | 
|  |  | 
|  | **Note:** | 
|  | You can still query against Map or HashMap fields without querying against a map index. For example, you can always create a regular range query on a single key in any Map or HashMap field. However, note that subsequent query lookups will be limited to a single key. | 
|  |  | 
|  | **Note:** | 
|  | Map indexes on all keys (when `*` is specified) are not used in queries where the map field is compared with `null` or when it is compared using `!=`, e.g. `p.positions['company1'] = null` or `p.positions['company1'] != '3'`. | 
|  | These types of queries will be executed without making use of the index, which could make them slower. | 
|  |  |