1. 程式人生 > 其它 >python使用者畫像_使用者畫像實戰,理論偏少。

python使用者畫像_使用者畫像實戰,理論偏少。

技術標籤:python使用者畫像

使用者畫像是啥?有啥用?這兩塊我就不多說了?主要介紹如何開發一個簡單的使用者畫像,在開發中介紹一些理論概念。開發流程
第一階段:目標解讀
在建立使用者畫像前,首先需要明確使用者畫像服務於企業的物件,根據業務方需求,未來產品建設目標和使用者畫像分析之後預期效果;
第二階段:任務分解與需求調研
經過第一階段的需求調研和目標解讀,我們已經明確了使用者畫像的服務物件與應用場景,接下來需要針對服務物件的需求側重點,結合產品現有業務體系和“資料字典”規約實體和標籤之間的關聯關係,明確分析緯度;
第三階段:需求場景討論與明確
在本階段,資料運營人員需要根據前面與需求方的溝通結果,輸出《產品使用者畫像規劃文件》,在該文件中明確畫像應用場景、最終開發出的標籤內容與應用方式 ,並就該份文件與需求方反覆溝通確認無誤。

第四階段:應用場景與資料口徑確認
經過第三個階段明確了需求場景與最終實現的標籤緯度、標籤型別後,資料運營人員需要結合業務與資料倉庫中已有的相關表,明確與各業務場景相關的資料口徑。在該階段中,資料運營方需要輸出《產品使用者畫像實施文件》,該文件需要明確應用場景、標籤開發的模型、涉及到的資料庫與表,應用實施流程;
第五階段:特徵選取與模型資料落表
本階段中資料分析挖掘人員需要根據前面明確的需求場景進行業務建模,寫好HQL邏輯,將相應的模型邏輯寫入臨時表中,抽取資料校驗是否符合業務場景需求。
第六階段:線下模型資料驗收與測試
資料倉庫團隊的人員將相關資料落表後,設定定時排程任務,進行定期增量更新資料。資料運營人員需要驗收數倉加工的HQL邏輯是否符合需求,根據業務需求抽取查看錶中資料範圍是否在合理範圍內,如果發現問題及時反饋給資料倉庫人員調整程式碼邏輯和行為權重的數值。
第七階段:線上模型釋出與效果追蹤
經過第六階段,資料通過驗收之後,就可以將資料介面給到搜尋、或技術團隊部署上線了。上線後通過對使用者點選轉化行為的持續追蹤,調整優化模型及相關權重配置。

使用者畫像來源以下主題表(維度)

使用者屬性

使用者行為

使用者偏好

使用者社交

使用者消費

等等

使用者畫像表結構設計

全量表設計
日全量資料表中,每天對應的日期分割槽中插入截止到當天為止的全量資料,使用者使用查詢時,只需查詢最近一天即可獲得最新全量資料。下面以一個具體的日全量表結構例子來做說明。

CREATE TABLE dw.userprofile_tag_userid (
tagid STRING COMMENT 'tagid',

userid STRING COMMENT 'userid',
tagweight STRING COMMENT 'tagweight',
reserve STRING COMMENT '預留' )
PARTITIONED BY (data_date STRING COMMENT '資料日期' ,tagtype STRING COMMENT '標籤主題分類')

這裡tagid表示標籤名稱,userid表示使用者id,tagweight表示標籤權重,reserve表示一個預留欄位。分割槽方式為(日期+標籤主題)分割槽,設定兩個分割槽欄位更便於開發和查詢資料。該表結構下的標籤權重僅考慮統計型別標籤的權重,如:歷史購買金額標籤對應的權重為金額數量,使用者近30日訪問天數為對應的天數,該權重值的計算未考慮較為複雜的使用者行為次數、行為型別、行為距今時間等複雜情況。通過全連線的方式與前面每天的資料做join關聯。

例如,對於主題型別為“會員”的標籤,插入‘20180701’日的全量資料,可通過語句:insert overwrite table dw.userprofile_tag_userid partition(data_date=’20180701’, tagtype=’member’)來實現。查詢截止到20180701日的被打上會員標籤的使用者量,可通過語句:select count(*) from dw.userprofile_tag_userid where data_date=’20180701’來實現。

標籤型別
使用者畫像建模其實就是對使用者進行打標籤,從對使用者打標籤的方式來看,一般分為三種類型:1、基於統計類的標籤;2、基於規則類的標籤、3、基於挖掘類的標籤。下面我們介紹這三種類型標籤的區別:統計類標籤:這類標籤是最為基礎也最為常見的標籤型別,例如對於某個使用者來說,他的性別、年齡、城市、星座、近7日活躍時長、近7日活躍天數、近7日活躍次數等欄位可以從使用者註冊資料、使用者訪問、消費類資料中統計得出。該類標籤構成了使用者畫像的基礎;規則類標籤:該類標籤基於使用者行為及確定的規則產生。例如對平臺上“消費活躍”使用者這一口徑的定義為近30天交易次數>=2。在實際開發畫像的過程中,由於運營人員對業務更為熟悉、而資料人員對資料的結構、分佈、特徵更為熟悉,因此規則類標籤的規則確定由運營人員和資料人員共同協商確定;機器學習挖掘類標籤:該類標籤通過資料探勘產生,應用在對使用者的某些屬性或某些行為進行預測判斷。例如根據一個使用者的行為習慣判斷該使用者是男性還是女性,根據一個使用者的消費習慣判斷其對某商品的偏好程度。該類標籤需要通過演算法挖掘產生。
在專案工程實踐中,一般統計類和規則類的標籤即可以滿足應用需求,開發中佔有較大比例。機器學習挖掘類標籤多用於預測場景,如判斷使用者性別是男是女,判斷使用者購買商品偏好、判斷使用者流失意向等。一般地機器學習標籤開發週期較長,耗費開發成本較大,因此其開發所佔比例較小。

標籤命名

標籤主題:用於刻畫屬於那種型別的標籤,如使用者屬性、使用者行為、使用者消費、風險控制等多種型別,可用A、B、C、D等字母表示各標籤主題;標籤型別:標籤型別可劃為分型別和統計型這兩種型別,其中分型別用於刻畫使用者屬於哪種型別,如是男是女、是否是會員、是否已流失等標籤,統計型標籤用於刻畫統計使用者的某些行為次數,如歷史購買金額、優惠券使用次數、近30日登陸次數等標籤,這類標籤都需要對應一個使用者相應行為的權重次數;開發方式:開發方式可分為統計型開發和演算法型開發兩大開發方式。其中統計型開發可直接從資料倉庫中各主題表建模加工而成,演算法型開發需要對資料做機器學習的演算法處理得到相應的標籤;是否互斥標籤:對應同一級類目下(如一級標籤、二級標籤),各標籤之間的關係是否為互斥,可將標籤劃分為互斥關係和非互斥關係。例如對於男、女標籤就是互斥關係,同一個使用者不是被打上男性標籤就是女性標籤,對於高活躍、中活躍、低活躍標籤也是互斥關係;使用者維度:用於刻畫該標籤是打在使用者唯一標識(userid)上,還是打在使用者使用的裝置(cookieid)上。可用U、C等字母分別標識userid和cookieid維度標籤舉例
對於使用者是男是女這個標籤,標籤主題是使用者屬性,標籤型別屬於分型別,開發方式為統計型,為互斥關係,使用者維度為userid。這樣給男性使用者打上標籤“A111U001_001”,女性使用者打上標籤“A111U001_002”,其中“A111U”為上面介紹的命名方式,“001”為一級標籤的id,後面對於使用者屬性維度的其他一級標籤可用“002”、“003”等方式追加命名,“_”後面的“001”和“002”為該一級標籤下的標籤明細,如果是劃分高、中、低活躍使用者的,對應一級標籤下的明細可劃分為“001”、“002”、“003”。

標籤開發

主要用 spark sql 語言採用python

人口屬性中 部分標籤舉例說明:

A220U083_001 累計購買金額
A220U084_001 最近一次購買距今天數
A220U087_001 累計購買次數
A220U088_001 註冊未購買

程式碼實現

#!/usr/bin/env python
# encoding: utf-8
from pyspark import SparkContext,SparkConf
from pyspark.sql import SparkSession
import sys
import datetime
def main():
start_date = sys.argv[1]
start_date_str = str(start_date)
format_1 = "%Y%m%d"
format_2 = "%Y-%m-%d"
strptime, strftime = datetime.datetime.strptime, datetime.datetime.strftime
old_date_partition = strftime(strptime(start_date_str, format_1), format_2)
target_table = 'dw.profile_tag_user'
# 累計購買金額
insert_all_paid_money = " insert overwrite table " + target_table + " partition(data_date="+"'"+start_date_str+"'"+",tagtype='userid_all_paid_money') \
select 'A220U083_001' as tagid, \
user_id as userid, \
sum(order_total_amount) as tagweight, \
'' as tagranking, \
'' as reserve, \
'' as reserve1 \
from dw.dw_order_fact \
where pay_status in (1,3) \
group by 'A220U083_001',user_id "
# 累計購買次數
insert_all_paid_times = " insert overwrite table " + target_table + " partition(data_date="+"'"+start_date_str+"'"+",tagtype='userid_all_paid_times') \
select 'A220U087_001' as tagid, \
user_id as userid, \
count(distinct order_id) as tagweight, \
'' as tagranking, \
'' as reserve, \
'' as reserve1 \
from dw.dw_order_fact \
where pay_status in (1,3) \
group by 'A220U087_001',user_id "
# 最近一次購買距今天數
insert_last_paid_days = " insert overwrite table " + target_table + " partition(data_date="+"'"+start_date_str+"'"+",tagtype='userid_last_paid') \
select 'A220U084_001' as tagid, \
t.user_id as userid, \
datediff(to_date("+"'"+old_date_partition+"'"+"),concat(substr(t.result_pay_time,1,10))) as tagweight, \
'' as tagranking, \
'' as reserve, \
'' as reserve1 \
from ( \
select user_id, \
result_pay_time, \
row_number() over(partition by user_id order by result_pay_time desc) as rank \
from dw.dw_order_fact \
where pay_status in (1,3) \
) t \
where t.rank =1 \
group by 'A220U084_001',t.user_id, \
datediff(to_date("+"'"+old_date_partition+"'"+"),concat(substr(t.result_pay_time,1,10)))"
# 註冊未購買
regist_notpaid = " insert overwrite table " + target_table + " partition(data_date="+"'"+start_date_str+"'"+",tagtype='userid_regist_notpaid') \
select 'A220U088_001' as tagid, \
user_id as userid, \
'' as tagweight, \
'' as tagranking, \
'' as reserve, \
'' as reserve1 \
from dim.dim_user_info \
where data_date = "+"'"+start_date_str+"'"+" \
and (paid_order_amount = 0 or paid_order_amount is null ) \
group by 'A220U088_001', user_id "
spark = SparkSession.builder.appName("userid_paidinfo").enableHiveSupport().getOrCreate()
spark.sql(insert_all_paid_money)
spark.sql(insert_all_paid_times)
spark.sql(insert_last_paid_days)
spark.sql(regist_notpaid)
if __name__ == '__main__':
main()

開發總結

你會發現開發就是從不同主題維度抽取需要的標籤並命名插到彙總使用者總標籤。

備註:如果行為日誌出現多個客戶標識,比如小明用ipad 安卓 蘋果等多個標識去產生行為,如果不做處理,很可能小明一個使用者產生多個使用者畫像。解決方案 採用 spark graph 圖計算進行去重。

9104ed9130c60ee2bcd7d86f9438d5a6.png

形成

// (g01,Set[im01,mac01,wx01])// (g02,Set[im02,mac02,wx02])

每一組就可以代表一個使用者,取一個使用者id 即可。重新整理日誌資料,將同一個id 進行歸一化,在進行使用者畫像標籤提取。這一塊雖然說的簡單 但是操作起來確實很麻煩。

標籤儲存

Mysql

MySQL在畫像中儲存的資料主要包括以下幾種型別:
1畫像標籤的元資料

包括:標籤id 標籤名 中文名 使用者主題 建立日期 修改日期 等
2結果集的校驗(標籤量級的監控、Hive同步到hbase的校驗、資料波動的校驗);

我們開發的標籤是放在hive 數倉裡,讀取比較麻煩,所以我們會同步到hbase 中方便業務進行呼叫。同步就會監控是否出現同步差異,所以就會在mysql 進行監控。這可以通過一個python 指令碼即可實現。
3同步到業務系統中的資料(業務方使用的資料庫,如客服系統使用的MySQL,使用sqoop同步相關的資料);

Hbase

將數倉裡標籤進行同步到hbase

a86af30eca697754deb8225906c9f48c.png

推送業務

針對不同業務進行推送使用者畫像資訊,我們也可以將使用者畫像儲存到es中,直接清晰化展示。如 搜尋某人 可以檢視 此人個人資訊 是否是重要價值客戶,消費情況,購買率,跳出率等等。

最終我們可以寫個整體排程過程 crontab 即可。

寫個python 排程指令碼

如下:

#!/usr/bin/env python

# -*- coding: utf-8 -*-

import sys

import datetime

import os

if len(sys.argv) < 2:

today = datetime.datetime.today()

oneday = datetime.timedelta(days=1)

yesterday = today - oneday

datestr = yesterday.strftime("%Y%m%d")

else:

datestr= sys.argv[1]

os.system("export PYTHONIOENCODING=utf8")

os.system("export SPARK_HOME=/usr/local/spark-2.1.1-bin-hadoop2.6")

os.system("export JAVA_HOME=/usr/local/jdk1.8.0_162/")

os.system("export PATH=$JAVA_HOME/bin:$PATH")

# 標籤開發

os.system("/usr/local/spark-2.1.1-bin-hadoop2.6/bin/spark-submit --master yarn --deploy-mode client --queue root.production.userprofile --driver-memory 1g --executor-memory 8g --executor-cores 2 --num-executors 50 /home/userprofile/userprofile_cookieid_gender.py " + datestr)

os.system("/usr/local/spark-2.1.1-bin-hadoop2.6/bin/spark-submit --master yarn --deploy-mode client --queue root.production.userprofile --driver-memory 1g --executor-memory 4g --executor-cores 2 --num-executors 50 /home/userprofile/userprofile_cookieid_country.py " + datestr)

# 校驗標籤

os.system("/usr/local/spark-2.1.1-bin-hadoop2.6/bin/spark-submit --master yarn --deploy-mode client --queue root.production.userprofile --driver-memory 4g --executor-memory 8g --executor-cores 2 --num-executors 50 /home/userprofile/checkdata_cookieid.py " + datestr)

os.system("/usr/local/spark-2.1.1-bin-hadoop2.6/bin/spark-submit --master yarn --deploy-mode client --queue root.production.userprofile --driver-memory 4g --executor-memory 8g --executor-cores 2 --num-executors 50 /home/userprofile/checkdata_userid.py " + datestr)

基本開發流程就這樣,寫的比較大概話,一個整體開發思路。

實現使用者畫像方法很多 hive sql spark core spark sql 都可以。

2e353dd96370053fceba50af3bdf1bd4.png2e353dd96370053fceba50af3bdf1bd4.png歡迎幫忙轉發關注我 微信公共賬戶2e353dd96370053fceba50af3bdf1bd4.png2e353dd96370053fceba50af3bdf1bd4.png2e353dd96370053fceba50af3bdf1bd4.png

53dbfd386ffd86587612597d2ccb3595.png

64a8fb25efbbd7d3976fe0ca6155e0e7.gif