【问题标题】:Count number of times a button was pressed in 15 minute chunks计算在 15 分钟内按下按钮的次数
【发布时间】:2011-07-18 13:30:01
【问题描述】:

我的应用程序有 24 个按钮来计算不同的车辆类型和方向(该应用程序将用于计算流量)。目前,每次按下按钮时,我都会将一行保存到 .csv 文件中。 csv文件包含时间戳、方向等。

我必须以 15 分钟的间隔测量每个按钮被按下的次数。

我应该如何存储按钮的计数器? 我只需要输出在 15 分钟内按下每个按钮的频率(每个按钮都有不同的标识标签)。

我在考虑使用 HashMap,它可以只将按钮的标签作为键,将出现的次数作为值,如下所示:

HashMap<String, Integer> hm = new HashMap<String, Integer>();

Integer value = (Integer) hm.get(buttonTag);
    if (value == null) {
        hm.put(buttonTag, 1);
    } else {
        int nr_occ = value.intValue() + 1;
        hm.put(buttonTag, nr_occ);
    }

但是,我不需要按钮按下的总和,而是 15 分钟的块。由于我已经将时间戳写入原始 csv 文件,我想知道如何存储这些值。

编辑:我目前正在测试 HashMap,它的计数效果非常好,但我发现了两个问题:首先,将其分组为 15 分钟的间隔,其次,hashmap 没有以任何方式排序.我需要输出按车辆类型和方向排序的值。

【问题讨论】:

  • 您是指在使用应用程序时将计数器存储在内存中的方式吗?如果是这样,您是否还需要显示应用程序之前运行的计数器?
  • 我只需要在应用程序使用时存储计数器,之前运行的计数器无关紧要。
  • @iDroid 当他们接到一个小时的电话并且活动被破坏时会发生什么?静态 int 再见。
  • @Emanuel 好的,用户碰巧点击了主页按钮......并不是说它实际上会,但在那时,即使只有一纳秒,您的活动也被标记为能够被系统。再次丢失任何未存储的活动数据。
  • 有人想对序列化方法发表评论吗?在 SharedPreferences 中放置非首选项似乎很奇怪。

标签: java android csv hashmap counter


【解决方案1】:

如果您的数据很简单(即您只需要一个键/值对),那么请考虑使用SharedPreferences 来存储按钮 ID 和按下时间。

这是一个好方法,因为它非常快。您已经将信息放入 .csv 文件,但提取数据并遍历它以便比较时间戳是 IMO 的太多开销。

按下按钮时,将您的数据存储在 .csv 文件中,然后还存储键/值(id/时间戳),然后您可以遍历它并进行比较并输出您需要输出的任何内容。

另一种方法(可能甚至更好)是简单地创建并写入您的 .csv 文件,然后转储它并使用其他更强大的东西来处理该数据,因为您可能会这样做。

编辑:我看到很多答案都说要使用 SQLite、静态等...

对于您的要求,这些都是劣质的方法。这就是为什么... SQLite 对于一个简单的按钮 ID 和时间戳来说太过分了。但是,如果您认为将来可能需要存储更多数据,这实际上可能是一种选择。

如果系统碰巧销毁 Activity,则静态变量可能会被销毁。

【讨论】:

  • 我必须存储时间戳、方向、转弯和车辆类型。当前 (direction,turn,vehicletype) 是按钮的标签。如何处理来自 csv 文件的原始数据?如果我的客户可以从设备中计算出来,我会非常棒,而无需运行脚本或其他东西。但是我将如何处理数据呢?
  • @Emanuel 尽管你说你只需要一个标识符和一个值。这就是 SharedPreferences 在 IMO 中大放异彩的地方。如果您愿意,您甚至可以每 15 分钟快速清除一次,然后重新开始写入,然后计算每个标识符有多少匹配项。
  • 关于 SQLite,我试过用 SQLite 来做,但就像你说的,这个相对简单的任务真的很复杂。而且我 100% 确信我们将来不需要存储更多数据。关于 SharedPreferences:所以我将按钮的标签存储为键,将时间戳存储为值。然后我会计算在 15 分钟的窗口中有多少次出现,然后处理这些?当用户单击停止按钮时,我会删除首选项吗?这样就够了吗?
  • 差不多...不过我会做一个更改...我会在您需要时在开始时清除文件。这是因为在应用程序关闭之前您可能永远没有机会清除文件,因此如果您认为在开始写入时已清除文件,则可能有旧的过时数据。
  • 在实例化首选项处理程序时创建一个新文件。您可以拥有任意数量的文件。
【解决方案2】:

如果您想变得,只需在每次您的活动被破坏时序列化HashMap (onDestroy) 并在您的活动被创建时重新加载它 (onCreate)。这将是最快和最简单的方法。

您要将数据序列化到哪里?到Environment.getExternalStorage()中的文件。

哦,您可能想要跟踪时间戳以每 15 分钟清除一次 HashMap - 您可以将其放入 SharedPreferences

我假设您已经知道如何执行此操作,但以防万一:Java Serialization

【讨论】:

  • 对不起这个问题,但为什么我需要序列化 ​​HashMap?因为我不知道我如何实际计算 15 分钟的块 - 是否已序列化。
  • 然后将其设为列表(或数组或仅制作二维数组)的 HashMap!使用时间戳 + System.currentTimeInMillis() 来确定我们在哪个索引上。然后你可以制作漂亮的图表。如果您的应用程序被破坏,整个序列化过程是为了保留您的“简单”数据(无论可能是什么)。
  • 所以我会使用序列化来确保数据保留在那里,以防应用程序关闭。这个列表的 HashMap 会是什么样子?我假设 HashMap 将包含按钮的标签作为键,而列表将包含时间戳?
  • 第一个问题,您希望将这些数据保留多长时间?
  • 是的,所以当用户按下“开始”时,您将当前系统时间记录到 SharedPreferences(以保持该值)。每按一次按钮,您将查看该值减去当前时间并除以 15 分钟以找出我们所处的 15 分钟时段。现在我们知道我们在哪个时段,更新右侧索引中哈希图中的计数在列表上(列表索引现在代表 15 分钟计数块)。按停止,写入 csv,清除所有数据,完成。
【解决方案3】:

可能是我,但这听起来是使用 SQLite 数据库的理想情况。因此,您可以通过选择时间戳轻松地从中获取此间隔。

【讨论】:

  • 我已经尝试过使用 SQLite 数据库来做这件事,但我不得不说我有点不知所措,因为我对 Android 开发一点经验都没有。但我真的开始认为 SQLite 真的是完美的选择。你能帮我处理数据库吗?我想我需要在每个应用程序启动时创建一个新表并存储这些数据:id、日期、时间、车辆类型、方向、转弯。然后选择我需要的数据并将数据写入一个新的csv文件?
猜你喜欢
  • 2014-10-04
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-03-14
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多