使用在第2个数据帧和第1个数据帧中形成的新行创建矩阵

时间:2017-10-28 11:45:51

标签: python pandas dataframe matrix

data1 = { 'node1': [1,1,1,2],
     'node2': [2,3,5,4],
     'weight': [1,1,1,1], }
df1 = pd.DataFrame(data1, columns = ['node1','node2','weight'])

data2 = { 'node1': [1,1,2,3],
     'node2': [4,5,4,5],
     'weight': [1,1,1,1], }
df2= pd.DataFrame(data2, columns = ['node1','node2','weight'])

我想创建一个矩阵,矩阵中的1表示在第二个数据帧中形成的新行。 例如,2 4是一个在两个数据帧中的行,因此在矩阵中我们将矩阵[2,4] = 0和[4,2] = 0作为关系是双向的。

2)1 4是第二个数据帧中的一个新行,它不在第一个数据帧中,所以我们把矩阵[1,4] = 1和[4,1] = 1

3)如果组合在dfs中看起来不像[3,4]那么它的矩阵[3,4] =矩阵[4,3] = 0

预期产出:

0 0 0 1 0
0 0 0 0 0
0 0 0 0 1
1 0 0 0 0
0 0 1 0 0

2 个答案:

答案 0 :(得分:2)

使用node*列作为numpy数组的索引器,可以非常轻松地完成此操作。

# Adapting Divakar's answer to my question here (with thanks) 
# https://stackoverflow.com/a/46990063/4909087 

m = pd.concat([df1, df2]).max().max()
v = np.zeros((m, m))

idx1 = df2.iloc[:, :-1].values - 1
idx2 = df1.iloc[:, :-1].values - 1

v[tuple(np.r_[idx1,idx1[:,::-1]].T)] = 1
v[tuple(np.r_[idx2,idx2[:,::-1]].T)] = 0

v
array([[ 0.,  0.,  0.,  1.,  0.],
       [ 0.,  0.,  0.,  0.,  0.],
       [ 0.,  0.,  0.,  0.,  1.],
       [ 1.,  0.,  0.,  0.,  0.],
       [ 0.,  0.,  1.,  0.,  0.]])

如果您想在数据框中输出,请调用DataFrame构造函数:

pd.DataFrame(v, np.arange(m) + 1, np.arange(m) + 1, dtype=int)

   1  2  3  4  5
1  0  0  0  1  0
2  0  0  0  0  0
3  0  0  0  0  1
4  1  0  0  0  0
5  0  0  1  0  0

答案 1 :(得分:2)

使用class SubmissionsController < ApplicationController include Wicked::Wizard steps :name, :details, :comments, :submit, :thankyou def show @company = Company.find(params[:company_id]) render_wizard end def update @company = Company.find(params[:company_id]) # one time checkout @amount = 50 @description = 'Premium Package' customer = Stripe::Customer.create( :email => params[:stripeEmail], :source => params[:stripeToken] ) Stripe::Charge.create( :customer => customer.id, :amount => @amount, :description => @description, :currency => 'eur' ) rescue Stripe::CardError => e flash[:error] = e.message params[:company][:status] = step.to_s params[:company][:status] = 'active' if step == steps.last @company.update_attributes(company_params) render_wizard @company end private ... ..

<%= form_for @company, url: wizard_path, method: :put do |f| %>
  <article>
    <% if flash[:error].present? %>
      <div id="error_explanation">
        <p><%= flash[:error] %></p>
      </div>
    <% end %>
    <label class="amount">
      <span>Amount: €0.50</span>
    </label>
  </article>

  <script src="https://checkout.stripe.com/checkout.js" class="stripe-button"
          data-key="<%= Rails.configuration.stripe[:publishable_key] %>"
          data-description=<% @description %>
          data-amount=<% @amount %>
          data-locale="auto"></script>
<% end %>