Index: trunk/src/org/openstreetmap/josm/actions/search/SearchAction.java
===================================================================
--- trunk/src/org/openstreetmap/josm/actions/search/SearchAction.java	(revision 8219)
+++ trunk/src/org/openstreetmap/josm/actions/search/SearchAction.java	(revision 8220)
@@ -349,4 +349,5 @@
                 .addKeyword("<i>key</i>=", null, tr("matches if ''key'' exists"))
                 .addKeyword("<i>key</i>><i>value</i>", null, tr("matches if ''key'' is greater than ''value'' (analogously, less than)"))
+                .addKeyword("\"key\"=\"value\"", "\"\"=\"\"", tr("to quote operators.<br>Within quoted strings the <b>\"</b> and <b>\\</b> characters need to be escaped by a preceding <b>\\</b> (e.g. <b>\\\"</b> and <b>\\\\</b>)."), "\"addr:street\"")
                 , GBC.eol());
         right.add(new SearchKeywordRow(hcbSearchString)
@@ -357,5 +358,4 @@
                 .addKeyword("-<i>expr</i>", null, tr("logical not"))
                 .addKeyword("(<i>expr</i>)", "()", tr("use parenthesis to group expressions"))
-                .addKeyword("\"key\"=\"value\"", "\"\"=\"\"", tr("to quote operators.<br>Within quoted strings the <b>\"</b> and <b>\\</b> characters need to be escaped by a preceding <b>\\</b> (e.g. <b>\\\"</b> and <b>\\\\</b>)."), "\"addr:street\"")
                 , GBC.eol());
 
@@ -379,5 +379,6 @@
             right.add(new SearchKeywordRow(hcbSearchString)
                 .addTitle(tr("properties"))
-                .addKeyword("nodes:<i>20-</i>", "nodes:", tr("objects with at least 20 nodes"))
+                .addKeyword("nodes:<i>20-</i>", "nodes:", tr("ways with at least 20 nodes, or relations containing at least 20 nodes"))
+                .addKeyword("ways:<i>3-</i>", "ways:", tr("nodes with at least 3 referring ways, or relations containing at least 3 ways"))
                 .addKeyword("tags:<i>5-10</i>", "tags:", tr("objects having 5 to 10 tags"))
                 .addKeyword("role:", "role:", tr("objects with given role in a relation"))
Index: trunk/src/org/openstreetmap/josm/actions/search/SearchCompiler.java
===================================================================
--- trunk/src/org/openstreetmap/josm/actions/search/SearchCompiler.java	(revision 8219)
+++ trunk/src/org/openstreetmap/josm/actions/search/SearchCompiler.java	(revision 8220)
@@ -29,4 +29,5 @@
 import org.openstreetmap.josm.tools.Geometry;
 import org.openstreetmap.josm.tools.Predicate;
+import org.openstreetmap.josm.tools.Utils;
 import org.openstreetmap.josm.tools.date.DateUtils;
 
@@ -99,5 +100,5 @@
     public class CoreSimpleMatchFactory implements SimpleMatchFactory {
         private Collection<String> keywords = Arrays.asList("id", "version",
-                "changeset", "nodes", "tags", "areasize", "waylength", "modified", "selected",
+                "changeset", "nodes", "ways", "tags", "areasize", "waylength", "modified", "selected",
                 "incomplete", "untagged", "closed", "new", "indownloadedarea",
                 "allindownloadedarea", "inview", "allinview", "timestamp", "nth", "nth%");
@@ -137,4 +138,6 @@
                     case "nodes":
                         return new NodeCountRange(tokenizer);
+                    case "ways":
+                        return new WayCountRange(tokenizer);
                     case "tags":
                         return new TagCountRange(tokenizer);
@@ -922,8 +925,11 @@
         @Override
         protected Long getNumber(OsmPrimitive osm) {
-            if (!(osm instanceof Way))
+            if (osm instanceof Way) {
+                return (long) ((Way) osm).getRealNodesCount();
+            } else if (osm instanceof Relation) {
+                return (long) ((Relation) osm).getMemberPrimitives(Node.class).size();
+            } else {
                 return null;
-            else
-                return (long) ((Way) osm).getRealNodesCount();
+            }
         }
 
@@ -931,4 +937,33 @@
         protected String getString() {
             return "nodes";
+        }
+    }
+
+    /**
+     * Matches objects with the number of referring/contained ways in the given range
+     */
+    private static class WayCountRange extends RangeMatch {
+        public WayCountRange(Range range) {
+            super(range);
+        }
+
+        public WayCountRange(PushbackTokenizer tokenizer) throws ParseError {
+            this(tokenizer.readRange(tr("Range of numbers expected")));
+        }
+
+        @Override
+        protected Long getNumber(OsmPrimitive osm) {
+            if (osm instanceof Way) {
+                return (long) Utils.filteredCollection(osm.getReferrers(), Way.class).size();
+            } else if (osm instanceof Relation) {
+                return (long) ((Relation) osm).getMemberPrimitives(Way.class).size();
+            } else {
+                return null;
+            }
+        }
+
+        @Override
+        protected String getString() {
+            return "ways";
         }
     }
