当前位置: 首页 > news >正文

VBA使用字典统计

Sub statistical_data()
    Dim lastRow As Long '每个sheet的最后一行
    Dim i As Long, j As Long
    Dim ws As Worksheet
    
    '按照任务紧急程度_紧急重要,重要不紧急,紧急不重要,不紧急不重要 作为key统计计划用时,和时间用时
    Dim emergency_dict As Object
    Set emergency_dict = CreateObject("Scripting.Dictionary")
    '按照任务分类平台作为KEY,统计 统计计划用时,和时间用时
    Dim task_dict As Object
    Set task_dict = CreateObject("Scripting.Dictionary")
    
    
    '定义要存储的数组 0存放计划用时,1存放实际用时
    Dim time_date(0 To 1) As Single
    Dim emergency_key As String, type_key As String
    Dim key As Variant
    'Dim col_max As Integer, countcol As Integer
    
    
    ' 设置目标工作表和列
    Set ws = ThisWorkbook.ActiveSheet   ' 修改为你的工作表名称
    
    
    Dim nums_of_columns As Long
    Dim row_max As Long, start_row As Long
    
    '最大的列
    nums_of_columns = ws.UsedRange.Columns.Count + 1
    row_max = ws.Range("D65535").End(xlUp).Row
    
    For i = 1 To row_max
     If ws.Range("D" & i) = "紧急程度" Then
        start_row = i + 1
        Exit For
     End If
    Next
    
    Dim task_countrow As Long, emergency_countrow As Long, emergency_start_row As Long, task_start_row As Long
    Dim emergency_end_row As Long, task_end_row As Long
    
    emergency_countrow = start_row + 1
    emergency_start_row = start_row + 1
    task_countrow = start_row + 7
    task_start_row = start_row + 7
    
    Dim plan_col As Long, actual_col As Long, result_col As Long, emergency_col As Long, type_col As Long
    For j = 2 To nums_of_columns
      If ws.Cells(start_row - 1, j) = "紧急程度" Then
        emergency_col = j
       End If
       
       If ws.Cells(start_row - 1, j) = "分类" Then
         type_col = j
       End If
       
      If ws.Cells(start_row - 1, j) = "计划投入时间(小时)" Then
        plan_col = j
      End If
    
      
      If ws.Cells(start_row - 1, j) = "实际投入时间(小时)" Then
         actual_col = j
      End If
       
       '按照紧急程度统计,写入数据的列
       If ws.Cells(start_row - 1, j) = "按照紧急程度统计" Then
          result_col = j
          Exit For
       End If
    Next
    
    Dim result_str_start As String, result_str_end As String, chart_end_col As String
    result_str_start = CNtoW(result_col)
    result_str_end = CNtoW(result_col + 3)
    chart_end_col = CNtoW(result_col + 2)
    
     
    
    
    Dim tempArray(0 To 1) As Single
    Application.ScreenUpdating = False
    '进行统计分析
    Dim emergency_string As String, type_string As String
    Dim plan_time As Single, actual_time As Single
    For i = start_row To row_max
        ' 在这里处理每一行的数据
        emergency_string = ws.Cells(i, emergency_col)
        type_string = ws.Cells(i, type_col)
        plan_time = CSng(ws.Cells(i, plan_col))
        actual_time = CSng(ws.Cells(i, actual_col))
        
        emergency_key = emergency_string
        type_key = type_string
        
        '查找emergency_dict字典是否存在
        If emergency_dict.Exists(emergency_key) Then
                '存在原来数据读出进行累加
                tempArray(0) = emergency_dict(emergency_key)(0) + plan_time
                tempArray(1) = emergency_dict(emergency_key)(1) + actual_time
                emergency_dict(emergency_key) = tempArray
        Else
               '不存在进行初始化
               time_date(0) = plan_time
               time_date(1) = actual_time
               emergency_dict.Add emergency_key, time_date
        End If
            
        '查找task_dict字典是否存在
        If task_dict.Exists(type_key) Then
                '存在原来数据读出进行累加
                tempArray(0) = task_dict(type_key)(0) + plan_time
                tempArray(1) = task_dict(type_key)(1) + actual_time
                task_dict(type_key) = tempArray
         Else
               '不存在进行初始化
               time_date(0) = plan_time
               time_date(1) = actual_time
               task_dict.Add type_key, time_date
        End If
        
    
    Next
    
    
    '清除历史残留,按照紧急程度的统计
    ws.Select
    Range(result_str_start & emergency_countrow & ":" & result_str_end & emergency_countrow + 3).Select
    Selection.ClearContents
    
    Dim task_row_max As Long
    '清除历史残留,按照任务统计
    task_row_max = ws.Range(result_str_start & 65535).End(xlUp).Row
   
    If task_row_max > task_countrow Then
        Dim startCell As String, endCell As String
        startCell = result_str_start & task_countrow
        endCell = result_str_end & (task_countrow + 3)
        
        ' 直接清除内容,避免使用Select/Selection
        ws.Range(startCell & ":" & endCell).ClearContents
    End If
    
    ' 删除工作表中的图表对象(嵌入式图表)
    For Each chartObj In ws.ChartObjects
        chartObj.Delete
    Next chartObj
    
    
   
    '数据写入
    Dim total_plan_times As Single, total_actual_times As Single
    total_plan_times = 0#
    total_actual_times = 0#
    For Each key In emergency_dict.Keys
       ws.Cells(emergency_countrow, result_col) = key
       total_plan_times = total_plan_times + emergency_dict(key)(0)
       ws.Cells(emergency_countrow, result_col + 1) = emergency_dict(key)(0)
       total_actual_times = total_actual_times + emergency_dict(key)(1)
       ws.Cells(emergency_countrow, result_col + 2) = emergency_dict(key)(1)
       ws.Cells(emergency_countrow, result_col + 3) = emergency_dict(key)(1) - emergency_dict(key)(0)
       emergency_countrow = emergency_countrow + 1
    Next key
    ws.Cells(start_row - 1, result_col + 1) = total_plan_times
    ws.Cells(start_row - 1, result_col + 2) = total_actual_times
    emergency_end_row = emergency_countrow - 1
    
   
    
    totalrow = start_row + 5
    For Each key In task_dict.Keys
       ws.Cells(task_countrow, result_col) = key
       ws.Cells(task_countrow, result_col + 1) = task_dict(key)(0)
       ws.Cells(task_countrow, result_col + 2) = task_dict(key)(1)
       ws.Cells(task_countrow, result_col + 3) = task_dict(key)(1) - task_dict(key)(0)
       task_countrow = task_countrow + 1
    Next key
    ws.Cells(totalrow, result_col + 1) = total_plan_times
    ws.Cells(totalrow, result_col + 2) = total_actual_times
    task_end_row = task_countrow - 1
    
    
    '画二维饼图
    Dim startDate As Date
    Dim emergency_chart_title As String, task_chart_title As String
    startDate = ThisWorkbook.ActiveSheet.Cells(1, 5).Value
    emergency_chart_title = "按照紧急程度统计时间使用情况" & FormatDateToNumeric(startDate)
    task_chart_title = "按照任务分类统计时间使用情况" & FormatDateToNumeric(startDate)
    '按照紧急程度统计时间图表
    'CreatePieChartWithCategoryLabels(start_col As String, end_col As String, start_row As Long, end_row As Long, chart_title As String)
    CreatePieChartWithCategoryLabels result_str_start, chart_end_col, emergency_start_row, emergency_end_row, emergency_chart_title
    CreatePieChartWithCategoryLabels result_str_start, chart_end_col, task_start_row, task_end_row, task_chart_title
    Application.ScreenUpdating = True
    
    MsgBox "The statistical time is completed."

End Sub

相关文章:

  • 键盘按键枚举 Key 说明文档
  • [创业之路-418]:经济学 - 凯恩斯主义的需求管理与西方供应侧理论、供需关系理论详解以及对创者者的启示
  • 【leetcode】78. 子集
  • 湖北理元理律师事务所债务规划方法论:法律框架下的可持续还款体系
  • 义乌购商品详情接口开发指南
  • 详解Java的启动参数-Dfile.encoding、System.getProperty(“file.encoding“)、该参数影响哪些行为
  • Atcoder Beginner Contest 410 题解报告
  • 生产者消费者消息流转和基本实操
  • Golang 在 Linux 平台上的并发控制
  • Vue3 + TypeScript + Element Plus 表格实例null检查方法
  • 18.vue.js的scoped样式隔离?原理和使用?(1)
  • c++总结-05-模板与泛型编程
  • 大IPD之——学习华为市场洞察,为战略找到方向(四)
  • 层压板选择、信号完整性和其他权衡
  • 日常开发工作流程梳理
  • 16 celery集成其他工具
  • 【论文解读】AgentThink:让VLM在自动驾驶中学会思考与使用工具
  • 【Python 爬虫 防盗链】
  • Java大模型开发入门 (12/15):Agent实战 - 打造能调用外部API的智能助手
  • STM32F4通用定时器TIM9-TIM14讲解及PWM呼吸灯实例解读
  • 做网站运营这工作怎么样/国内免费顶级域名注册
  • 专业的网页设计和网站制作公司/seo快速排名是什么
  • 办公家具网站模版/中国足彩网竞彩推荐
  • 没有备案的网站百度能收录吗/宁波网站推广优化哪家正规
  • 网络建设服务与网站运营推广/惠州网站排名提升
  • 哪个网站做h5号/海南百度推广电话