【问题标题】:How to add (sum) the two values in a python dictionary based on another value?如何根据另一个值在python字典中添加(求和)两个值?
【发布时间】:2013-12-23 20:31:28
【问题描述】:

我正在使用 jasper 在openerp 中创建 2 个报告。但我对 2 个报告使用相同的解析器,第一个报告是“详细报告”,第二个报告是“摘要”。在附加到结果列表的字典(命名数据)中,有键日期、发票、借方和贷方。对于详细报告,我只需要从account.move.line 获取这些值。但是对于汇总报告,应该只有一行包含相同发票编号的帐户移动行。那就是我需要添加具有相同发票编号的帐户移动行的借方和贷方并将其显示为一行,我该如何在Python中做到这一点。例如结果列表是

[{'invoice':1,'debit':10,'credit':10},
 {'name':'b','invoice':2,'debit':10,'credit':18},
 {'invoice':1,'debit':10,'credit':10}]

而我需要的是

[{'invoice':1,'debit':20,'credit':20},
 {'invoice':2,'debit':10,'credit':18}]

编辑: 代码是

move_line_ids = move_line_pool.search(cr, uid, domain, context=context)
        print 'move_line_ids', len(move_line_ids)

        for move_line in move_line_pool.browse(cr, uid, move_line_ids, context=context):
            group_by = grp = grp_acc = ''
            debit = credit = bal = 0.0
            if move_line.debit > 0.0:
                debit = move_line.amount_residual
            elif move_line.credit > 0.0:
                credit = move_line.amount_residual
            bal = debit - credit    
            if form_group_by == 'group_account_code':
                group_by = 'ACCOUNT CODE : '
                grp = move_line.account_id.code or ''
                grp_acc = move_line.account_id.name or ''
            elif form_group_by == 'group_order_no':
                group_by = 'ORDER : '
                grp = move_line.sale_id.name or ''
            else:
                group_by = 'INVOICE : '
                grp = move_line.invoice.number or ''
            date = dt.strptime(str(move_line.date), '%Y-%m-%d').strftime('%d-%m-%Y')

            data = {
                        'period': period,
                        'date': date,
                        'company': company or '',
                        'so': move_line.sale_id.name or '',
                        'invoice': move_line.invoice.number or '',
                        'po': '',
                        'status': '',
                        'ref': move_line.move_id.name or '',
                        'debit': debit,
                        'credit': credit,
                        'bal': bal,
                        'fc': '',
                        'f_amt': '',
                        'trx': move_line.journal_id.code or '',
                        'account': move_line.account_id.name or '',
                        'account_code': move_line.account_id.code or '',
                        'acc_range': acc_range,
                        'group_by': group_by,
                        'grp': grp,
                        'grp_acc': grp_acc,
            }

            result.append(data)

        if form_group_by == 'group_account_code':
            result = sorted(result, key=lambda k: k['account_code'])
        elif form_group_by == 'group_order_no':
            result = sorted(result, key=lambda k: k['so'])
        else:
            result = sorted(result, key=lambda k: k['invoice'])
        return result

只考虑字典中的键invoice,debit and credit,如果发票相同则不需要更新其他键。

【问题讨论】:

  • 确实可以用python来完成,但我相信最好通过sql groupby/sum来完成。请展示一些代码如何产生你的第一个输出。
  • @alko 我已经更新了问题..

标签: python dictionary openerp


【解决方案1】:

假设我理解你的问题,这样的事情就可以解决问题:

sum_dict = {}

对于 source_list 中的 e:
    如果 sum_dict.keys() 中的 e["invoice"]:
        sum_dict[e["invoice"]]["debit"]+=e["debit"]
        sum_dict[e["invoice"]]["credit"]+=e["credit"]
    别的:
        sum_dict[e[“发票”] = e

result_list = [sum_dict[k] for k in sum_dict.keys()]

预计到达时间:

在添加代码之前,我回答了基本问题。会更新。

预计到达时间 2:

好的,我认为这是一个在 for 循环和 if/else 块之间运行的简单修复。

但是,正如评论者所指出的,最好的解决方法可能是对您的数据库调用的逻辑进行一些更改。不过,我知道的还不够多,无法提出好的改变。

【讨论】:

    【解决方案2】:

    可能不是最佳答案...

    li_dict =[{'invoice':1,'debit':10,'credit':10},{'name':'b','invoice':2,'debit':10,'credit':18},
    {'invoice':1,'debit':10,'credit':10}, {'name':'b','invoice':2,'debit':10,'credit':18}]
    
    
    final_result = []
    for dic in li_dict :
        temp_dict = {}
        flag = False
    
        for dic_f in final_result:
            if 'invoice' in dic and 'invoice' in dic_f:
                if dic['invoice'] == dic_f['invoice']:
                    dic_f['debit'] = dic['debit'] + dic_f['debit']
                    dic_f['credit'] = dic['credit'] + dic_f['credit']
                    flag = True
                    break
    
        if not flag:
            temp_dict['invoice'] = dic.get('invoice', 0)
            temp_dict['debit'] = dic.get('debit', 0)
            temp_dict['credit'] = dic.get('credit', 0)
            final_result.append(temp_dict)
    
    print final_result
    

    结果:

    [{'credit': 20, 'invoice': 1, 'debit': 20}, {'credit': 18, 'invoice': 2, 'debit': 10}]
    

    【讨论】:

    • 这可以通过稍后创建列表来更轻松地完成,但如果内存比速度更重要,我会这样做。
    猜你喜欢
    • 2019-06-19
    • 2022-07-10
    • 2019-09-04
    • 2019-05-15
    • 1970-01-01
    • 2016-04-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多