按距离查询客户端统计数据

尝试一下在线预览

此示例演示如何在 FeatureLayerView 中按距离查询统计数据,以及如何在一系列图表中显示查询结果。

此应用程序显示 2007 年至 2017 年间来自 50 个美国城市的凶杀数据。这些数据由《华盛顿邮报》收集和分析,可在此处下载

当用户在视图中拖动游标时,应用程序将使用 FeatureLayerView 查询并高亮显示游标位置一英里内的所有要素。随着游标位置的变化,图表会立即更新为新数据。

     
1
2
3
4
5
view.on("drag", function(event) {
  // query the layer view for each pointer drag event
  // then display the results in the charts
  queryStatsOnDrag(layerView, event).then(updateCharts);
});

工作原理

要按距离查询图层视图,首先需要创建查询对象并设置所需的参数。FeatureLayer 上的 createQuery()  方法是使用在对象上定义的图层的所有当前配置来构造此对象的便捷方法。

       
1
2
3
4
5
6
7
const query = layerView.layer.createQuery();
// converts the screen point to a map point
// the event object is returned from the drag event
query.geometry = view.toMap(event);
// queries all features within 1 mile of the point
query.distance = 1;
query.units = "miles";

接下来,创建 StatisticDefinition 对象数组,为要查询统计数据的每个字段设置字段名称和统计数据类型。对于统计数据查询,可以查询字段名称或从 SQL 表达式返回的数据的统数据。此示例为每个指针拖动执行近 30 个统计数据查询。在以下代码段中,我们只会显示其中的几个。

                                                              
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
// clone the query object from the previous snippet
const statsQuery = query.clone();

// date used to calculate the average time a case has been opened
const dataDownloadDate = Date.UTC(2018, 6, 5);

// Create the statistic definitions for querying stats from the layer view
// the `onStatisticField` property can reference a field name or a SQL expression
// `outStatisticFieldName` is the name of the statistic you will reference in the result
// `statisticType` can be sum, avg, min, max, count, stddev
const statDefinitions = [
  // Age of crime since it was reported in years

  {
    onStatisticField: "(" + dataDownloadDate + " - milliseconds) / (1000 * 60 * 60 * 24 * 365.25)",
    outStatisticFieldName: "avg_open_time_years",
    statisticType: "avg"
  },

  // total homicides

  {
    onStatisticField: "1",
    outStatisticFieldName: "total",
    statisticType: "count"
  },

  // crime disposition (aka crime status)
  //
  // Since this is a string field, we can use a similar technique to sum
  // the total of each status of the crime

  {
    onStatisticField: "CASE WHEN disposition = 'Closed by arrest' THEN 1 ELSE 0 END",
    outStatisticFieldName: "num_closed_arrest",
    statisticType: "sum"
  },
  {
    onStatisticField: "CASE WHEN disposition = 'Open/No arrest' THEN 1 ELSE 0 END",
    outStatisticFieldName: "num_open",
    statisticType: "sum"
  },
  {
    onStatisticField: "CASE WHEN disposition = 'Closed without arrest' THEN 1 ELSE 0 END",
    outStatisticFieldName: "num_closed_no_arrest",
    statisticType: "sum"
  },

  // average victim age
  //
  // Some victim ages are unknown and indicated with a -99. We'll
  // use an expression to treat those unknown ages as 0. This will
  // skew the average age slightly downward since we can't exclude those
  // values without a where clause. Do use a where clause, we could execute
  // a separate query

  {
    onStatisticField: "CASE WHEN victim_age_years = -99 THEN 0 ELSE victim_age_years END",
    outStatisticFieldName: "avg_age",
    statisticType: "avg"
  }
];

创建统计数定义对象后,将它们作为数组传递给 Query 对象的 outStatistics 属性,然后执行查询。

             
1
2
3
4
5
6
7
8
9
10
11
12
13
// add the stat definitions to the the statistics query object cloned earlier
statsQuery.outStatistics = statDefinitions;

// execute the query for all features in the layer view
return layerView.queryFeatures(statsQuery).then(
  function(response) {
    const stats = response.features[0].attributes;
    return stats;
  },
  function(e) {
    console.error(e);
  }
);

若要仅查询数据的子集,可以选择在 Query 对象上设置 where 子句。

               
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
// clone the query object from the previous steps
const openStatsQuery = statsQuery.clone();
// limit the results to only the crimes that did not result in an arrest
openStatsQuery.where = "disposition = 'Open/No arrest'";

// execute the query for only unsolved homicides in the layer view
return layerView.queryFeatures(openStatsQuery).then(
  function(response) {
    const stats = response.features[0].attributes;
    return stats;
  },
  function(e) {
    console.error(e);
  }
);

结果将作为 FeatureSet 中的单个要素返回。每个统计数据的属性名称是在 StatisticDefinition 对象中设置的 outStatisticFieldName 的名称。请参阅下图,该图显示了其中一个查询的结果在打印到浏览器控制台时的外观。

flv-query-stats-result

Your browser is no longer supported. Please upgrade your browser for the best experience. See our browser deprecation post for more details.