7
$\begingroup$

The two formats documented for EntityClass are

EntityClass["type",name]
EntityClass["type",{property1->value1, property2->value2}]

It appears as if my intended use would require input of the form below, which is not allowed.

EntityClass["type",name,{property1->value1, property2->value2}]

I am attempting to find the 100 public high schools closest to my college.

(* Let's say my college is in Brockport, NY *)
bport = Entity["City",{"Brockport", "NewYork", "UnitedStates"}]["Position"];
(* Get public high school data *)
ps = EntityClass["PublicSchool", {"USState", "NewYork"}];

Right now, I'm using two steps to cull the desired information from the EntityClass. First, I create a list of schools with their distances to Brockport and their grade spans, then filter the (sorted) list to exclude schools that serve students below 7th grade.

distanceToBPort = 
 MapThread[{#3, #1, GeoDistance[bport, #2]} &, 
 Transpose@ps[{"Name", "Coordinates", "GradeSpan"}]];
subset = SortBy[
   Select[distanceToBPort, (#[[1]] =!= Missing["NotAvailable"]) && ( 
       Head[#[[3]]] =!= GeoDistance) &&
      Not@MemberQ[#[[1]], "pre-kindergarten" | "kindergarten", 2] &&
      #[[1, 1]] > 6
     &
    ], Last];

The selection/filtering is not optimal and probably removes valid entries, but the point here is that I should be able to create an implicit entity class rather than converting into a List. My approach, as presented, eliminates the location information, which I need to create a map, although I can work around that by redesigning the MapThread statement.

The question: What is the appropriate, effective way to filter an EntityClass defined by EntityClass["type",name] while maintaining an Entity-type head?

A similar question has been asked; however, I don't think it relates to the current problem (unless I'm completely misinterpreting the relationship between the 2nd argument types in EntityClass).

$\endgroup$
  • $\begingroup$ EntityClass[..., name] is pretty much just a short-hand for EntityClass[..., filteringRules], even if the filter is "Name"->MemberQ[nameAlternatives]. What you'll want is EntityClass["PublicSchool", {"State"->..., "Location"->TakeSmallestBy[distanceToBrockPort, 10]] or something. $\endgroup$ – b3m2a1 Nov 14 '18 at 20:15
  • $\begingroup$ @b3m2a1 I'm not sure how to implement that suggestion, since the components of name ("USState" and "NewYork") are not properties of the school entities that are in the EntityClass. $\endgroup$ – bobthechemist Nov 15 '18 at 2:19
  • $\begingroup$ There’s surely some form of location property right? You can do the filtering off that I imagine $\endgroup$ – b3m2a1 Nov 15 '18 at 3:34
  • 2
    $\begingroup$ To find the nearest high schools I'd use schools = GeoNearest[ps, bport, 100]. You can check the distances with GeoDistance[bport, schools]. $\endgroup$ – jose Nov 15 '18 at 6:03
  • $\begingroup$ @jose that's getting me in the right direction $\endgroup$ – bobthechemist Nov 15 '18 at 12:53
1
$\begingroup$

This is more of a workaround. If you're willing and able to preload the data, you could create your own custom Entity type with EntityStore and treat it as if it were a built in.

Your data:

bport = Entity["City", {"Brockport", "NewYork", "UnitedStates"}]["Position"];
ps = EntityClass["PublicSchool", {"USState", "NewYork"}];

The nearby schools, per Jose's comment above:

ents = GeoNearest[ps, bport, 100];

Create the custom entity. For brevity I omit custom labels, properties, classes, etc.

store = EntityStore[
  "NearbyPublicSchools" -> <|
    "Entities" -> EntityValue[ents, "EntityPropertyAssociation"]
  |>
];

EntityRegister[store];

Query as if it were a built in type. For example:

largefaculty = EntityClass["NearbyPublicSchools", 
  {"TotalTeachers" -> GreaterThan[Quantity[50, "People"]]}];

largefaculty["EntityCount"]
28
GeoListPlot[largefaculty]

enter image description here


Here's another workaround, but unfortunately your example returns Missing["QueryTooSlow"].

EntityClass["PublicSchool", 
  {"Entity" -> ps, "TotalTeachers" -> GreaterThan[Quantity[200, "People"]]}
]["EntityCount"]
Missing["QueryTooSlow", {"PublicSchool", {EntityProperty["PublicSchool", "Entity"] -> EntityClass["PublicSchool", {"USState", "NewYork"}]}}]

Here's a smaller example:

EntityClass["Lattice", 
  {"Entity" -> EntityClass["Lattice", "Even"], "Determinant" -> GreaterThan[10]}
]["EntityCount"]
6
$\endgroup$
  • $\begingroup$ It may be a workaround; however, I'm doubtful that a non-workaround answer is available with the current version of Mathematica. $\endgroup$ – bobthechemist Dec 17 '18 at 13:11
0
$\begingroup$

Nominally this should work as a pure EntityClass query...

EntityClass[
  "PublicSchool",
  {
   "Position" ->
    TakeSmallestBy[
     With[{h = Here},
      If[MissingQ[#], Quantity[ 10^10, "Miles"], GeoDistance[#, h]] &
      ], 
     10
     ]
   }
  ] // EntityList

But it'll be slow as no pre-curation has been done. Making subqueries on an EntityClass doesn't seem to be supported. I'm not sure how this could be sped up, though, and I haven't had the patience to wait for the query to finish.

$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.