0

顧客データのcsvファイルがあり、過去の行動に基づいて顧客が製品を購入する確率を調べたいと思います。

テーブルは次のようになります。

custId         prodId       purchased
   001           0001          0
   002           0001          0
   006           1001          1
   001           0501          0
   012           8001          0
   189           0071          0
   487           0001          1
   ...           ...          ...

custIdは顧客ID、は製品です。顧客は同じ製品を複数回表示できるため、prodId列は一意でも一意でもありません。custId-prodId

理想的な出力は次のようになります。

 custId         purchased
   001           .0999
   002           0
   006           1
   012           0
   189           .75
   487           1
   ...          ...   

bashファイルが大きすぎてメモリに収まらないため、これを実行することを検討しています。

助言がありますか?

4

2 に答える 2

1

Jonah Bishopとchorobaはどちらも、Perlを使用する必要があるとコメントしているので、私は同意する傾向があるので、Perlを使用してこれを行うBashコマンドを次に示します。

perl -e \
  ' use warnings;
    use strict;
    my %custCounts;
    my %custSums;
    while(<>)
    {
      m/^(\d{3}),\d{4},([01])$/
        or die "ruakh doesn'"'"'t understand your CSV file format";
      ++$custCounts{$1};
      ++$custSums{$1} if $2;
    }
    foreach my $custId (sort keys %custCounts)
    {
      print "$custId,", ($custSums{$custId}||0) / $custCounts{$custId}, "\n";
    }
  ' < customerData.csv

上記は、CSVファイルが次のようになっていることを前提としています。

001,0001,0
002,0001,0
006,1001,1
001,0501,0
012,8001,0
189,0071,0
487,0001,1

フィールドはそれぞれ3桁、4桁、0または1です。そうでない場合は、で始まる行を調整する必要がありますm/

于 2012-09-20T18:24:59.723 に答える
1

以下を使用した簡単な例を次に示しawkます。

awk '{++shown[$1]; if ($3 > 0) ++purchased[$1];}END{for (cust in purchased) print cust, purchased[cust]/shown[cust]}' datafile

エラーチェックはないので、入力がずれると死んでしまいます。さらに、ヘッダーなどを削除するために前処理を行う必要があります。フィールド区切り文字が空白でない場合は、「awk -F、...」を使用してフィールド区切り文字を「、」などに設定します。

また、これはゼロ以外のパーセンテージのエントリのみを出力し、すべての顧客を含めるには、に変更for (cust in purchased)for (cust in shown)ます。

于 2012-09-20T18:25:19.423 に答える