C# Querying with distance help

364 views
Skip to first unread message

Ali

unread,
Apr 26, 2012, 12:33:49 PM4/26/12
to mongodb-user
Hi I am using the 10gen Driver for c# 1.4.1 with Linq.

I have a query that finds multiple criteria from IQueryable as
follows:-
var result = col.asquerable();
result = result.where(cond1);
result=result.where(cond2);
result = result.where(cond3) etc to filter down the results;

What I would like is the final search before i show the results to be
less than a distance i specify. I have lon/lat stored in the
collection as location:{long,lat}

i want to pass in the current users long/lat which i have as two vars
already plus the distance they wish to search below i.e < 30 miles.

How can I create this a one query, i would be happy to do it without
linq if need be and use the raw way of building the query.

Thanks in advance.

craiggwilson

unread,
Apr 26, 2012, 1:15:46 PM4/26/12
to mongod...@googlegroups.com
The linq support has the ability to inject a lower level query.  You can use the LinqToMongo.Inject method to insert this into the query.  Remember that longitude goes first, latitude second.  "Location" is the name of the field containing the coordinates.

            var query = collection.AsQueryable();
 
            query = query.Where(x => x.FirstName == "Jack");
            query = query.Where(x => x.LastName == "McJack");
            query = query.Where(x => LinqToMongo.Inject(Query.Near("Location", -96.770401, 32.816774, 20)));

Ali

unread,
Apr 26, 2012, 3:10:06 PM4/26/12
to mongod...@googlegroups.com
Thanks will try this and see what happens I appreciate the quick response

Ali

unread,
Apr 27, 2012, 12:35:06 PM4/27/12
to mongod...@googlegroups.com
What is the default passing in valude, i.e would 50 be miles or kilometers? How do I set it to miles?

craiggwilson

unread,
Apr 27, 2012, 12:52:34 PM4/27/12
to mongod...@googlegroups.com
That is a complicated answer and depends on whether you are doing spherical queries or not.  Read the docs here for more information:  http://www.mongodb.org/display/DOCS/Geospatial+Indexing#GeospatialIndexing-geoNearCommand.  

Ali

unread,
Apr 27, 2012, 4:01:07 PM4/27/12
to mongod...@googlegroups.com
Craig thanks.  What i want to do is the following:
Query the db as you suggestion end up with my object say Persion
Which would contain Location array/long/lat
And then use a c# method which will use the long//lat and convert it to miles (this i have already) but what i was wondering is would it give me km by default as my c# method would convert this.
Thanks again.

craiggwilson

unread,
Apr 28, 2012, 6:37:19 PM4/28/12
to mongod...@googlegroups.com
I believe in this case, if you are not doing the spherical model, then your distance value would be in degrees because that is the unit of your coordinates.  If you were using the spherical model, your units would be in radians.  

You'll want to do a google search of how to convert miles to degrees.  It will be a simple matter of multiplying by a constant.

Ali

unread,
May 27, 2012, 4:39:30 PM5/27/12
to mongod...@googlegroups.com
Hi finally got around to trying this with the following error:
failed: Exception has been thrown by the target of an invocation.
System.Reflection.TargetInvocationException: Exception has been thrown by the target of an invocation. ---> System.InvalidOperationException: The LinqToMongo.Inject method is only intended to be used in LINQ Where clauses.
at MongoDB.Driver.Linq.LinqToMongo.Inject(IMongoQuery query)
at lambda_method(Closure )
  --- End of inner exception stack trace ---

On Thursday, April 26, 2012 5:33:49 PM UTC+1, Ali wrote:

craiggwilson

unread,
May 28, 2012, 6:21:33 PM5/28/12
to mongod...@googlegroups.com
Can you post the code you are using so we can see what you are doing?  As the exception states, there is no implementation of LinqToMongo.Inject.  It is designed to only be used in a query that will get translated to mongodb.  If it is evaluated locally, then it will throw this message.  

Ali

unread,
May 29, 2012, 5:48:08 AM5/29/12
to mongod...@googlegroups.com
Sure, its exactly as you suggested using the latest driver from 10gen gained from NuGet

            var query = collection.AsQueryable();
 
            query = query.Where(x => x.FirstName == "Jack");
            query = query.Where(x => x.LastName == "McJack");
            query = query.Where(x => LinqToMongo.Inject(Query.Near("Location", -96.770401, 32.816774, 20)));
-

The only difference is my field is called clocation.

On Thursday, April 26, 2012 5:33:49 PM UTC+1, Ali wrote:

craiggwilson

unread,
May 29, 2012, 7:36:37 AM5/29/12
to mongod...@googlegroups.com
This just a copy of what I showed above.  I'd like to see your code, plus the surrounding bits.  This code doesn't throw any exceptions when I run it.  

Ali

unread,
Jun 24, 2012, 8:45:13 PM6/24/12
to mongod...@googlegroups.com
Still can't get this to work.

Yes it was a copy of what you wrote that is what I am trying.  I am using the latest 10gen driver and will try and give as much background as I can.

My code:
            var query = All();
            query = query.Where(x => LinqToMongo.Inject(Query.Near("clocation", -0.737054, 51.636162, 1500)));
            return query.ToList();

All is defined as

        public IQueryable<T> All()
        {
            return this.collection.AsQueryable<T>();
        }

Which seems to be working on all queries so far apart from this distance one.

the name "clocation" is the name of the field in the document which looks like:-

clocation:[-xxxx,xxxxx] x-representing long/lat as per your suggested order.

I have taken a look at the profile table and it seems like the query does not even reach the database.

Do i need to run a command in the shell on this field or something.

Again thanks for the assitance.

Regards

Regards

On Thursday, April 26, 2012 5:33:49 PM UTC+1, Ali wrote:

craiggwilson

unread,
Jun 25, 2012, 7:58:49 AM6/25/12
to mongod...@googlegroups.com
You need to have an index specified on the clocation field...  see this link for more information:  http://www.mongodb.org/display/DOCS/Geospatial+Indexing 

Ali

unread,
Jun 26, 2012, 3:59:10 PM6/26/12
to mongod...@googlegroups.com
Turns out it is non of those things as I created the Indexes when I first started.  I hope this helps someone else who might face a similar issue.
The problem was a reference to the Fluent Mongo Library where Linq was being used from that library and not the MongoDriver library.

Thanks Craig for your help.


On Thursday, April 26, 2012 5:33:49 PM UTC+1, Ali wrote:
Reply all
Reply to author
Forward
0 new messages