android判斷點擊次數_Android應用統計-使用時長及次數統計(一)

關鍵字: 應用統計 Android源碼 應用使用時長 應用使用次數

最近在做有關于應用統計有關的工作,主要是統計系統中客戶端應用(非系統自帶的那些基礎應用,比如DownLoadManager),在每一天的使用情況,統計內容包括:應用打開次數,應用合計使用時長等。

在所搜尋的方案中,大致有如下兩種:

方案一:自行記錄每次activity的打開和關閉,根據這些數據進行統計。

方案二:使用系統自行記錄的每次activity的打開和關閉數據,進行統計。

以下方案采用兩個方案并行,主要是以系統數據統計結果為主,以自行記錄的數據作為參照,用以對比兩組數據,以保證數據統計結果的有效性和穩定性。

系統數據

在Android中,系統會自行記錄應用的打開次數和使用時間,且提供了相關api于開發者,但是每一次版本提升都可能會對api帶來相當大的改變,這一塊也不例外。但是始終沒有變化的就是在撥號鍵盤輸入* # * #4636# * #*,進入工程模式,點擊“使用情況統計數據”,你就可以看到統計界面了。由于各個版本之間差異比較大,而且相關的資料也比較少,本次使用的api以及相關的說明都是以Android-5.1為基礎。在某些版本中,應用統計api,存在不少缺陷以及避坑的地方,尤其是手機廠家修改過源碼之后,所以對于某些品牌的測試機器,程序的運行結果會有一點不一樣,請各位讀者有所注意。

如何獲取系統數據

第一步:獲取權限

在manifest文件中注冊該權限

在系統setting應用中打開相應開關,準許demo應用獲取數據。如果不執行這一步的話,demo將無法讀取系統數據。

測試機 : 小米4C。

打開目錄 : 設置 -〉其他高級設置 -〉安全和隱私 -〉有權查看使用情況的應用。界面如下圖:

第二步:獲取數據

獲取系統統計信息:

@SuppressWarnings("ResourceType")

@TargetApi(Build.VERSION_CODES.LOLLIPOP)

public static ArrayList getUsageList(Context context, long startTime, long endTime) {

Log.i(TAG," EventUtils-getUsageList() Range start:" + startTime);

Log.i(TAG," EventUtils-getUsageList() Range end:" + endTime);

Log.i(TAG," EventUtils-getUsageList() Range start:" + dateFormat.format(startTime));

Log.i(TAG," EventUtils-getUsageList() Range end:" + dateFormat.format(endTime));

ArrayList list = new ArrayList<>();

UsageStatsManager mUsmManager = (UsageStatsManager) context.getSystemService("usagestats");

Map map = mUsmManager.queryAndAggregateUsageStats(startTime, endTime);

for (Map.Entry entry : map.entrySet()) {

UsageStats stats = entry.getValue();

if(stats.getTotalTimeInForeground() > 0){

list.add(stats);

Log.i(TAG," EventUtils-getUsageList() stats:" + stats.getPackageName() + " TotalTimeInForeground = " + stats.getTotalTimeInForeground());

}

}

return list;

}

獲取系統記錄的詳細的各個activity的使用情況:

@SuppressWarnings("ResourceType")

@TargetApi(Build.VERSION_CODES.LOLLIPOP)

public static ArrayList getEventList(Context context, long startTime, long endTime){

ArrayList mEventList = new ArrayList<>();

Log.i(TAG," EventUtils-getEventList() Range start:" + startTime);

Log.i(TAG," EventUtils-getEventList() Range end:" +endTime);

Log.i(TAG," EventUtils-getEventList() Range start:" + dateFormat.format(startTime));

Log.i(TAG," EventUtils-getEventList() Range end:" + dateFormat.format(endTime));

UsageStatsManager mUsmManager = (UsageStatsManager) context.getSystemService("usagestats");

UsageEvents events = mUsmManager.queryEvents(startTime, endTime);

while (events.hasNextEvent()) {

UsageEvents.Event e = new UsageEvents.Event();

events.getNextEvent(e);

if (e != null && (e.getEventType() == 1 || e.getEventType() == 2)) {

Log.i(TAG," EventUtils-getEventList() "+e.getTimeStamp()+" event:" + e.getClassName() + " type = " + e.getEventType());

mEventList.add(e);

}

}

return mEventList;

}

獲取系統記錄的各個應用的使用次數:

由于該字段不能通過api拿到,故而采取反射的形式,拿到該字段。(注:其實該字段的統計數據并不可靠,一旦強行關機,比如拔電池,就可能失去數據,所以在系統代碼中該字段是被隱藏的。當然關于數據的可靠性,在接下來的文章中會有更詳細的說明)

private int getLaunchCount(UsageStats usageStats) throws IllegalAccessException {

Field field = null;

try {

field = usageStats.getClass().getDeclaredField("mLaunchCount");

} catch (NoSuchFieldException e) {

e.printStackTrace();

}

return (int) field.get(usageStats);

}

結語:

本文主要介紹了關于Android系統中統計各個app的使用情況的解決方案,以及獲取相關數據的方法。關于系統記錄的數據的原理以及在該原理的邏輯下可能出現的bug,將會在接下來的文章中詳細闡述。

轉載請注明出處。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/531909.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/531909.shtml
英文地址,請注明出處:http://en.pswp.cn/news/531909.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

linux+cp+-rdf,簡單構建基于RDF和SPARQL的KBQA(知識圖譜問答系統)

本文主要通過python實例講解基于RDF和SPARQL的KBQA系統的構建。該項目可在python2和python3上運行通過。注&#xff1a;KBQA即是我們通常所說的基于知識圖譜的問答系統。這里簡單構建的EasyKBQA&#xff0c;數據來源于網絡&#xff0c;源碼地址看下面補充說明。目錄&#xff1a…

java中Object.equals()簡單用法

/* equals&#xff08;&#xff09;方法默認的比較兩個對象的引用&#xff01; */ class Child {int num;public Child(int x){num x;}//人文的拋出運行時異常的好處是&#xff1a;可以自定義錯誤信息&#xff01;/*public boolean equals(Object o) throws ClassCastExceptio…

cmd imp導入dmp文件_oracle導入dmp文件的2種方法

使用imp、impdp方式導入數據1.使用imp導入數據打開cmd窗口&#xff0c;然后直接敲入一下命令即可&#xff0c;需要注意的是&#xff0c;要事先把dmp文件放到正確的路徑中去imp yx_base/yx_192. file E:\yxb\yx_base.dmp log E:\yxb\yx_base.log full y2.使用impdp導入數據(1…

from server sql 拼接統計兩個子查詢_[SQL SERVER系列]之嵌套子查詢和相關子查詢

子查詢有兩種類型&#xff0c;一種是只返回一個單值的子查詢&#xff0c;這時它可以用在一個單值可以使用的地方&#xff0c;這時子查詢可以看作是一個擁有返回值的函數&#xff1b;另外一種是返回一列值的子查詢&#xff0c;這時子查詢可以看作是一個在內存中臨時存在的數據表…

java中包容易出現的錯誤及權限問題

/* 3&#xff0c;權限在不同地方的體現&#xff1a; public protected default private 同一類中&#xff1a; ok ok ok ok 同一包中&#xff1a; ok ok ok 子類中&#xff1a; ok ok …

c語言程序算一元二次方程,如何用C語言來計算一元二次方程

C語言實現一元二次方程的解 源程序#include#includefloat x1,x2,p,q,d;float great_than_zero(float,float);float equql_to_zero(float,float);float smaller_than_zero(float,float);main(){float a,b,c;printf(“Enter a,b,c:”);scanf(“%f%f%f”,&a,&b,&c);db…

cosin等于多少_cos45度等于多少

cos45度√2/2。角A的鄰邊比斜邊叫做角A的余弦&#xff0c;記作cosA(由余弦英文cosine簡寫得來)&#xff0c;即cosA等于角A的鄰邊/斜邊(直角三角形)。二倍角公式sin2α2sinαcosαtan2α2tanα/(1-tan^2(α))cos2αcos^2(α)-sin^2(α)2cos^2(α)-11-2sin^2(α)積化和差公式sinα…

c語言宏定義比較三個數大小,C語言中兩個宏進行大小對比,其中一個沒有定義,這種行為如何定義。...

1.C語言中兩個宏進行大小對比&#xff0c;其中一個沒有定義&#xff0c;這種行為如何定義呢&#xff1f;在學習U-boot的過程中遇到這么一個定義&#xff1a;# if (CONFIG_ENV_ADDR > CONFIG_SYS_MONITOR_BASE) && \(CONFIG_ENV_ADDR CONFIG_ENV_SIZE) < \(CONFI…

java中變量運算細節 (2)

/* 目的&#xff1a;測試變量的運算方式 結果&#xff1a;byte a, b, c;a bc;或者 a b10形如這種形式的算式&#xff0c; 等式的右邊的運算結果默認的都是int型的&#xff01;因為等式右邊有變量&#xff0c; 編譯器無法確定變量的內容&#xff0c;因為它是變量&#xff01;所…

c語言設計二級考試程序修改題,全國計算機二級考試C語言復習題與答案解析

全國計算機二級考試C語言復習題與答案解析三、程序修改題下列給定程序中函數fun的功能是&#xff1a;將長整型數中各位上為奇數的數依次取出&#xff0c;構成一個新數放在t中。高位仍在高位&#xff0c;低位仍在低位。例如&#xff0c;當s中的數為87653142時&#xff0c;t中的數…

ccs變量觀察窗口在哪_CCS3.3查看變量圖形

CCS3.3查看變量圖形首先聲明&#xff0c;覺得ccs3.3中Graph并不是什么量都可以觀察的&#xff0c;原因是跟斷點有關&#xff0c;反正對于我的仿真器XDS510的是如此。即程序運行到斷點處會有延時&#xff0c;對于普通信號可能沒什么影響&#xff0c;但對于高頻信號來說&#xff…

poj 2777(線段樹的節點更新策略)

1 /*2 之前的思想是用回溯的方式進行顏色的更新的&#xff01;如果用回溯的方法的話&#xff0c;就是將每一個節點的顏色都要更新3 通過子節點的顏色情況來判斷父節點的顏色情況 &#xff01;這就是TLE的原因&#xff01;4 5 后來想一想沒有必要 &#xff01;加入[a, b] 區間有…

c語言計算機編程例題詳解,計算機C語言編寫程序題及答案解析精選.doc

計算機C語言編寫程序題及答案解析精選2011年計算機二級C語言編寫程序題及答案解析精選【4.1】已知銀行整存整取存款不同期限的月息利率分別為&#xff1a;0.315% 期限一年0.330% 期限二年月息利率 &#xff1d; 0.345% 期限三年0.375% 期限五年0.420% 期限八年要求輸入存錢的本…

mfsort shell語法_Shell中字符串排序的幾種方法

Shell中字符串排序的幾種方法【方法一】按ASCII正向排序備注:1) tr將子字符串中的空白轉換為換行符&#xff0c;再用sort排序2) sort無參的話&#xff0c;默認按ASCII正向排序【方法二】按ASCII正向排序備注:1) -r參數: 按ASCII碼反向排序2) 在使用sort,uniq等組合命令時候【方…

java中并不是任意多個接口都可以實現多實現

interface A{public abstract void show(); }interface B{public abstract int show(); }public class Test implements A, B{public void show(){System.out.println("A show!");}/*只寫 void show&#xff08;&#xff09;出現的問題&#xff1a;Test不是抽象的, 并…

變形監測期末復習_寒假即將來臨,中小學期末考試時間是什么時候?

2019年下學期也快結束&#xff0c;各個區的中小學考試時間安排已經公布了。今年&#xff0c;初二將首次進行全市統考&#xff0c;統考的意義重大&#xff0c;希望家長們可以督促孩子們重視起來&#xff0c;考出好成績!下面&#xff0c;讓我們來看一下2019下學期深圳各區中小學期…

c語言2048項目報告,c語言----項目_小游戲2048

2048 小游戲 主要是針對邏輯思維的一個訓練.主要學習方面:1.隨機數產生的概率.2.行與列在進行移動的時候幾種情況.3.messagebox的使用#include #include #include #include using namespace std;int board[4][4] {0}; //二維數組int if_need_rand; //是否生成隨機數int if_gam…

java中的顯示初始化和特定初始化

public class Test{public static void main(String[] args){Child child new Child();} }class Parent{public Parent(){super();show();//this.show(); 因為是Child類對象調用了super()來構造其父類的部分;所以父類中的this&#xff08;隨著其構造方法入棧的&#xff09;是指…

etl工程師 面試題_數據倉庫工程師面試題筆試.doc

數據倉庫工程師面試題姓名&#xff1a;____張小核______ 開始時間&#xff1a;_____:______ 結束時間&#xff1a;_____:_____數據庫使用過哪些數據庫&#xff1f;試說出它們的異同。答&#xff1a;使用過SQL SERVER和ORACLE它們的區別是&#xff1a;1.sql server 是中小型企業…

為什叫c語言,為什么c語言叫c語言?

1972年&#xff0c;美國貝爾實驗室的 D.M.Ritchie 在B語言的基礎上最終設計出了一種新的語言&#xff0c;他取了BCPL的第二個字母作為這種語言的名字&#xff0c;這就是C語言。1973年初&#xff0c;C語言的主體完成。Thompson和Ritchie用它完全重寫了UNIX。隨著UNIX的發展&…