android - Firebase 大查询 - 如何从自定义事件表中检索数据

标签 android mysql firebase google-bigquery firebase-analytics

我正在开发连接 Firebase 数据库的应用程序,我的应用程序基本上是一个市场应用程序。我已将所有用户搜索历史记录作为自定义事件记录到 Firebase Analytics,我已将其链接到大查询以用于分析或建议目的。

这是我的自定义事件日志示例:

FirebaseAnalytics mFireBaseAnalytics = FirebaseAnalytics.getInstance(context);
        Bundle params = new Bundle();
        params.putString("SEARCHER_ID", "xxxx_id");
        params.putString("KEYWORDS", "Shoe");
        params.putDouble("LATITUDE", 12.00);
        params.putDouble("LONGITUDE", 80.00);
        mFireBaseAnalytics.logEvent("SEARCH_PRODUCT", params);

此数据将保存在 app_events 表中的 Biq 查询中。

从这个事件中,我必须查询在我本地流行的关键字列表搜索,例如在 5 公里范围内。我不太确定如何实现这一目标。因为请参阅下面的结果,它实际上是如何存储在大查询中的。

"event_dim": [      
      {
        "date": "20170718",
        "name": "SEARCH_PRODUCT",
        "params": [

          {
            "key": "LATITUDE",
            "value": {
              "string_value": null,
              "int_value": null,
              "float_value": null,
              "double_value": "12.9632747"
            }
          },

          {
            "key": "SEARCHER_ID",
            "value": {
              "string_value": "-KkphUBI3_v3kdGq6qTa",
              "int_value": null,
              "float_value": null,
              "double_value": null
            }
          },

          {
            "key": "LONGITUDE",
            "value": {
              "string_value": null,
              "int_value": null,
              "float_value": null,
              "double_value": "80.2131347"
            }
          },

          {
            "key": "KEYWORDS",
            "value": {
              "string_value": "shoe cloths",
              "int_value": null,
              "float_value": null,
              "double_value": null
            }
          },

        ],

      }
      ]

对于这种格式,我使用标准 SQL 查询进行了如下查询

SELECT
SQRT(POW(69.1*( (
  SELECT
    params.value.double_value
  FROM
    x.params
  WHERE
    params.key = 'LATITUDE') - 12.00), 2) + POW(69.1*(80.098 - (SELECT
    params.value.double_value
  FROM
    x.params
  WHERE
    params.key = 'LONGITUDE') ) * COS((SELECT
    params.value.double_value
  FROM
    x.params
  WHERE
    params.key = 'LATITUDE') / 57.3), 2)) AS distance,
  (
  SELECT
    params.value.string_value
  FROM
    x.params
  WHERE
    params.key = 'KEYWORDS') AS KEYWORDS,
  (
  SELECT
    params.value.string_value
  FROM
    x.params
  WHERE
    params.key = 'SEARCHER_ID') AS SEARCHER_ID,
  (
  SELECT
    params.value.string_value
  FROM
    x.params
  WHERE
    params.key = 'LATITUDE') AS LATITUDE,
  (
  SELECT
    params.value.string_value
  FROM
    x.params
  WHERE
    params.key = 'LONGITUDE') AS LONGITUDE
FROM
  `app_name.app_events_*`,
  UNNEST(event_dim) AS x
WHERE
  x.name = 'SEARCH_PRODUCT'
  AND (
  SELECT
    params.value.string_value As SearchId
  FROM
    x.params
  WHERE
    params.key = 'SEARCHER_ID' ) = '-xx_id'

对于此查询,我面临 2 个问题。 1)我得到的距离为空 2) 我不确定如何在 5 公里范围内过滤此结果。

帮我解决这个问题。

附言: 我有另一个临时 Biqquery 表,我直接向其中插入数据,然后我可以使用以下查询从中获得预期结果。

SELECT
  SQRT(POW(111.1*( MAX(Lattitude) - 12.9632691), 2) + POW(111.1*(80.2140816 -  MAX(Longitude) ) * COS( MAX(Lattitude) / 57.3), 2)) AS distance,
  MAX(SearchKeyword) as SearchKeyword,
  SearcherArea,
  COUNT( SearcherArea) AS totalCount
FROM
  `HNF.LastFewHoursData`
WHERE
 SearchKeyword LIKE '%%'
GROUP BY
  SearcherArea

HAVING
  distance <= 5
ORDER BY
  totalCount DESC
LIMIT
  5

所以我只有在查询由 Firebase Analytics 更新的事件表时遇到问题。

最佳答案

这个查询可能对你有用:

CREATE TEMP FUNCTION distance(lat1 FLOAT64, lat2 FLOAT64, lon1 FLOAT64, lon2 FLOAT64) AS((
WITH data AS(
SELECT POW(SIN((ACOS(-1) / 180 * (lat1 -lat2)) / 2), 2) + COS(ACOS(-1) / 180 * (lat1)) * COS(ACOS(-1) / 180 * (lat2)) * POW(SIN((ACOS(-1) / 180 * (lon1 -lon2)) / 2), 2) a
)
SELECT 6371 * 2 * ATAN2(SQRT((SELECT a FROM data)), SQRT(1 - (SELECT a FROM data)))
));

WITH data AS(
  SELECT ARRAY<STRUCT<name STRING, params ARRAY<STRUCT<key STRING, value STRUCT<string_value STRING, int_value INT64, float_value FLOAT64, double_value FLOAT64> > > > > [STRUCT("SEARCH_PRODUCT" AS name, [STRUCT("LATITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.9632747 AS double_value) AS value), STRUCT("LONGITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 80.2131347 AS double_value) AS value), STRUCT("SEARCHER_ID" AS key, STRUCT("-KkphUBI3_v3kdGq6qTa" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value), STRUCT("KEYWORDS" AS key, STRUCT("shoes cloths" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value)] AS params),
                                                                                                                                                                          STRUCT("SEARCH_RANDOM" AS name, [STRUCT("LATITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.9632747 AS double_value) AS value), STRUCT("LONGITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 80.2131347 AS double_value) AS value), STRUCT("SEARCHER_ID" AS key, STRUCT("-KkphUBI3_v3kdGq6qTa" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value), STRUCT("KEYWORDS" AS key, STRUCT("shoes cloths" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value)] AS params),
                                                                                                                                                                          STRUCT("SEARCH_PRODUCT" AS name, [STRUCT("LATITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.9632747 AS double_value) AS value), STRUCT("LONGITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 80.2131347 AS double_value) AS value), STRUCT("SEARCHER_ID" AS key, STRUCT("-xx_id" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value), STRUCT("KEYWORDS" AS key, STRUCT("shoes cloths" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value)] AS params)] event_dim UNION ALL

  SELECT ARRAY<STRUCT<name STRING, params ARRAY<STRUCT<key STRING, value STRUCT<string_value STRING, int_value INT64, float_value FLOAT64, double_value FLOAT64> > > > > [STRUCT("SEARCH_PRODUCT" AS name, [STRUCT("LATITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.9632747 AS double_value) AS value), STRUCT("LONGITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 80.2131347 AS double_value) AS value), STRUCT("SEARCHER_ID" AS key, STRUCT("-KkphUBI3_v3kdGq6qTa" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value), STRUCT("KEYWORDS" AS key, STRUCT("shoes cloths" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value)] AS params),
                                                                                                                                                                          STRUCT("SEARCH_RANDOM" AS name, [STRUCT("LATITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.9632747 AS double_value) AS value), STRUCT("LONGITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 80.2131347 AS double_value) AS value), STRUCT("SEARCHER_ID" AS key, STRUCT("-KkphUBI3_v3kdGq6qTa" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value), STRUCT("KEYWORDS" AS key, STRUCT("shoes cloths" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value)] AS params),
                                                                                                                                                                          STRUCT("SEARCH_PRODUCT" AS name, [STRUCT("LATITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.9632747 AS double_value) AS value), STRUCT("LONGITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 80.2131347 AS double_value) AS value), STRUCT("SEARCHER_ID" AS key, STRUCT("-xxx_id" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value), STRUCT("KEYWORDS" AS key, STRUCT("shoes cloths" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value)] AS params)] event_dim UNION ALL

  SELECT ARRAY<STRUCT<name STRING, params ARRAY<STRUCT<key STRING, value STRUCT<string_value STRING, int_value INT64, float_value FLOAT64, double_value FLOAT64> > > > > [STRUCT("SEARCH_PRODUCT" AS name, [STRUCT("LATITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.01 AS double_value) AS value), STRUCT("LONGITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.01 AS double_value) AS value), STRUCT("SEARCHER_ID" AS key, STRUCT("-xx_id" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value), STRUCT("KEYWORDS" AS key, STRUCT("pants" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value)] AS params),
                                                                                                                                                                          STRUCT("SEARCH_PRODUCT" AS name, [STRUCT("LATITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.01 AS double_value) AS value), STRUCT("LONGITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.01 AS double_value) AS value), STRUCT("SEARCHER_ID" AS key, STRUCT("-xx_id" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value), STRUCT("KEYWORDS" AS key, STRUCT("shoes cloths" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value)] AS params),
                                                                                                                                                                          STRUCT("SEARCH_PRODUCT" AS name, [STRUCT("LATITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.01 AS double_value) AS value), STRUCT("LONGITUDE" AS key, STRUCT("" as string_value, 0 AS int_value, 0.0 AS float_value, 12.01 AS double_value) AS value), STRUCT("SEARCHER_ID" AS key, STRUCT("-xx_id" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value), STRUCT("KEYWORDS" AS key, STRUCT("shoes cloths" as string_value, 0 AS int_value, 0.0 AS float_value, 0.0 AS double_value) AS value)] AS params)] event_dim



)

SELECT
  keyword,
  count(1) freq
FROM(
  SELECT
    ARRAY(SELECT AS STRUCT (SELECT value.string_value FROM UNNEST(params) WHERE key = 'KEYWORDS' AND EXISTS(SELECT 1 FROM UNNEST(params) WHERE key = 'SEARCHER_ID' and value.string_value = '-xx_id')) AS keyword, (SELECT value.double_value FROM UNNEST(params) WHERE key = 'LATITUDE' AND EXISTS(SELECT 1 FROM UNNEST(params) WHERE key = 'SEARCHER_ID' and value.string_value = '-xx_id')) latitude, (SELECT value.double_value FROM UNNEST(params) WHERE key = 'LONGITUDE' AND EXISTS(SELECT 1 FROM UNNEST(params) WHERE key = 'SEARCHER_ID' and value.string_value = '-xx_id')) longitude FROM UNNEST(event_dim) WHERE name = 'SEARCH_PRODUCT') data
  FROM data
  WHERE EXISTS(select 1 FROM UNNEST(event_dim) WHERE (SELECT COUNTIF(value.string_value = '-xx_id') FROM UNNEST(params) WHERE key = 'SEARCHER_ID' ) > 0)
),
UNNEST(data)
WHERE keyword IS NOT NULL AND latitude IS NOT NULL AND longitude IS NOT NULL
AND distance(latitude, X, longitude, Y) < 5 -- change X and Y to your desired location
GROUP BY keyword
ORDER BY freq DESC

我做了什么:

首先我们有函数的定义 distance计算两个空间点之间的距离(以度为单位,例如,(纬度 12°,经度 13°))。

data只是对您在 Firebase 库中拥有的相同数据的模拟。运行查询时,只需替换 data用你的实际 table .

最后,查询本身首先过滤掉名称不是 SEARCH_PRODUCT 的事件在使用关键字及其纬度和经度构建 ARRAY 时(还有一个过滤器可以删除不等于 SEARCHER_ID-xx_id )。

在那之后,只有一个选择和一个 WHERE子句仅选择经纬度小于您要查询的所需位置的关键字(我在查询中将其称为 X 和 Y,您可以将其更改为您当前的位置,例如 12.09°、39.01°) .

让我知道这是否适合您。

关于android - Firebase 大查询 - 如何从自定义事件表中检索数据,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45237137/

相关文章:

java - Android 锁屏事件?

android - Flutter 中使用 dart 的视频编辑器

mysql - Pentaho Kettle - 如何根据结果集生成更新查询?

javascript - 我需要检测我的云函数中何时只有某个字段发生了变化

ios - 如何访问 childByAutoID 下的 Firebase 数据?

java - eclipse 中的 Junit 在使用 junit 时产生 NoClassDefFoundError

android - 如何将字体类型设置为webview

php - 如何舍入数字mysql行结果

mySQL使用表的值作为字段来获取查询

javascript - 离线使用 Firebase Angular 应用程序