excel学习库

excel表格_excel函数公式大全_execl从入门到精通

Excel VBA 工程项目报价表数据提取整理/格式调整

本文于2023年8月18日首发于本人同名其他平台,更多文章案例请搜索关注!

内容提要

  • 工程项目报价表数据提取整理

  • 格式调整

大家好,我是冷水泡茶,有位粉丝朋友在文章【Excel VBA 按同一个项目合并单元格文字】下面留言:

说实话,看文字还真没看明白,我就让他把文件发我瞅瞅,原来他是要把工程报价表中的C列的部分文字合并,填到D列(插入列),他的源表是这样的:

中间还有一个分页:

他的需求表是这个样子的:

我经过一番研究,分析他原来数据的规律,正如他所说,跟我前面分享的案例有几分相似,我们一起来看一看吧

基本思路

1、把不需要的标题删除,我们可以通过删除B列为空的行。

2、目标表的表头字段与原表的表头字段不完全一样,索性删除重新添加,可以通过查找关键字的方法定位到表头行,将其删除。

3、最难的地方,是把B列为空的单元格,对应的C列单元格的字符连起来,还要跳过两个工程名称行。

4、在C列后面插入一列,把拼接好的字段填到D列对应的项目名称行。

5、把B列为空的行,除了两个工程名称行,统统删除。

程序代码

1、ManipulateData,操作数据:

Sub ManipulateData()    Dim sourceWs As Worksheet    Dim targetWs As Worksheet    Dim wsName As String    Dim lastRow As Integer    Dim tbTitle(), strMerge As String    Dim rng As Range    Dim arrWidth()    Application.ScreenUpdating = False    Set sourceWs = ThisWorkbook.ActiveSheet    arrWidth = Array(5, 15, 15, 50, 8, 10, 12, 16)    wsName = "清洗表"    If sourceWs.Name = wsName Then Exit Sub    tbTitle = Array("序号", "项目编码", "项目名称", "项目特征描述", "计量单位", "工程量", "综合单价", "合价")    Call CopyWorksheet(sourceWs, wsName)    '删除小计行以下的行    Set targetWs = ThisWorkbook.Sheets(wsName)    With targetWs        lastRow = targetWs.UsedRange.Rows.Count        For i = lastRow To 1 Step -1            If Cells(i, 3) = "" Then                Rows(i).Delete            End If        Next        For i = lastRow To 1 Step -1            If InStr(Cells(i, 3), "小") > 0 And InStr(Cells(i, 3), "计") > 0 Then                Rows(i & ":" & lastRow).Delete            End If        Next        For i = lastRow To 1 Step -1            If InStr(Cells(i, 3), "名称") > 0 And InStr(Cells(i, 3), "特征") > 0 Then                Rows(i).Delete            End If        Next        .Columns(4).Insert Shift:=xlToRight        .Columns("I:I").Delete        .Rows(1).Insert Shift:=xlDown        .Range("A1").Resize(1, UBound(tbTitle) + 1) = tbTitle        lastRow = targetWs.UsedRange.Rows.Count        For i = 4 To lastRow            If .Cells(i, 2) <> .Cells(i - 1, 2) Then                m = i                If .Cells(i, 2) <> "" Then                    k = i                End If            End If            If .Cells(i, 2) <> .Cells(i + 1, 2) Then                If .Cells(i, 2) = "" Then                    If InStr(Cells(i, 3), "工程") > 0 Then                        n = i - 1                    Else                        n = i                    End If                    For j = m To n                        strMerge = strMerge & .Cells(j, 3) & Chr(10)                    Next                    strMerge = Left(strMerge, Len(strMerge) - 1)                    .Cells(k, 4) = strMerge                    strMerge = ""                End If            ElseIf Cells(i + 1, 3) = "" Then                n = i                For j = m To n                    strMerge = strMerge & .Cells(j, 3) & Chr(10)                Next                strMerge = Left(strMerge, Len(strMerge) - 1)                .Cells(k, 4) = Trim(strMerge)                strMerge = ""            End If            If .Cells(i, 3) = "" Then Exit For        Next        lastRow = .UsedRange.Rows.Count        For i = lastRow To 3 Step -1            If .Cells(i, 2) = "" Then                If InStr(Cells(i, 3), "工程") = 0 Then                    .Rows(i).Delete                End If            End If        Next        lastRow = .UsedRange.Rows.Count        .Rows(2).ClearFormats        With .Range(Cells(1, 1), Cells(lastRow, 3))            .ClearFormats            .VerticalAlignment = xlCenter        End With        With .Range(Cells(1, 6), Cells(lastRow, 8))            .ClearFormats            .VerticalAlignment = xlCenter            .NumberFormatLocal = "_ * #,##0.00_ ;_ * -#,##0.00_ ;_ * ""-""??_ ;_ @_ "        End With        With .Cells(1, 1).Resize(lastRow, UBound(tbTitle) + 1)            .Borders.LineStyle = xlDot            ' 边框线的样式为连续线            .Borders.Weight = xlThin ' 边框线的粗细为细线            .Borders.ColorIndex = xlAutomatic  ' 边框线的颜色为自动        End With        .Cells.Font.Size = 11        .Rows(1).HorizontalAlignment = xlCenter        .Columns(1).HorizontalAlignment = xlCenter        For i = LBound(arrWidth) To UBound(arrWidth)            .Columns(i + 1).ColumnWidth = arrWidth(i)        Next    End With    Call DeleteButtons(targetWs)    targetWs.Rows.AutoFit    targetWs.Range("A1").Select    Application.ScreenUpdating = TrueEnd Sub

代码解析:

(1)定义一些变量

(2)把源工作表sourceWs设为当前活动工作表。

(3)arrWidth数组,存放目标表的列宽,最后完成的表的列宽就按照这个数组的值来顺序确定,可根据需要调整。

(4)设置目标表名称wsName,如果当前活动工作表的名称也等于wsName,说明源表不对,直接退出过程

(5)tbTitle ,存放新表头字段名称。

(6)Call CopyWorksheet 复制源工作表为目标工作表。

(7)把targetWs设为复制的新表,下面的操作均针对targetWs进行。

(8)通过循环,删除“所有空白行。这里要从下往上删除。

(9)通过循环,删除“小计”以下的所有行。这里他的小计中间有空格,我们用Instr函数判断是否同时包含“小”和“计”,不管有多少空格就不受影响了。

(10)通过循环,删除表头行。这里跟删除小计行差不多,判断是否包含“名称”和“特征“两个字段。

(11).Columns(4).Insert Shift:=xlToRight,在第4列也就是D列插入一列。删除多余的I列,有格式。

(12) .Rows(1).Insert Shift:=xlDown,第一行插入空白行。接着把tbTitle的字段写入第一行。

(13)从第4行开始循环,寻找定位需要组合字符的行,m表示开头,n表示结尾,k表示项目编码或项目名称行,后面字符组合完成后,填入D列,k行。

(14)拼接字符填充完毕后,把不需要的行删除,就是上面的m~n行,但我们在删除的时候,采用删除B列空行的方法,跳过工程名称那一行。

(15)接着,设置单元格的格式,包括对齐,划线,数字格式等。

(16)Call DeleteButtons,删除目标工作表中的所有按钮。

2、其他过程:CopyWorksheetDeleteButtons

Sub CopyWorksheet(sourceWorksheet As Worksheet, wsName As String)    Dim targetWorksheet As Worksheet    '检查是否存在同名的目标工作表,如果存在则删除    On Error Resume Next    Set targetWorksheet = ThisWorkbook.Worksheets(wsName)    On Error GoTo 0    If Not targetWorksheet Is Nothing Then        Application.DisplayAlerts = False        targetWorksheet.Delete        Application.DisplayAlerts = True    End If    '复制源工作表到同一个工作簿    sourceWorksheet.Copy After:=ThisWorkbook.Sheets(ThisWorkbook.Sheets.Count)    '获取新复制的工作表的引用    Set targetWorksheet = ThisWorkbook.Sheets(ThisWorkbook.Sheets.Count)    '重命名新复制的工作表    targetWorksheet.Name = wsNameEnd SubSub DeleteButtons(ws As Worksheet)    Dim obj As OLEObject    '循环遍历工作表上的所有 OLE 对象(包括命令按钮)    For Each obj In ws.OLEObjects        obj.Delete ' 删除命令按钮    NextEnd Sub

代码解析:

(1)CopyWorksheet,复制工作表,过程参数:源工作表sourceWorksheet,新工作表名wsName ,把“源工作表”复制成以“新工作表名”命名的工作表。

(2)DeleteButtons,删除目标工作表中的所有按钮,我们直接复制工作表,连按钮也会一起复制过来,需要把它们删除

总结

1、本文涉及了很多工作表的操作,比如,复制工作表,删除行、列,插入行,设置单元格的格式等。

2、像今天的案例,如果用数组来处理,就没有直接操作工作表来得方便了,因为数组插入、删除行列是非常麻烦的,没有工作表来得快。

3、如果数据量特别大,在数组里操作也是可行的。这里就不再展开。

---End---

喜欢就点个、点在看留个言呗!分享一下更给力!感谢!

发表评论:

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。

«    2024年12月    »
1
2345678
9101112131415
16171819202122
23242526272829
3031
控制面板
您好,欢迎到访网站!
  查看权限
网站分类
搜索
最新留言
    文章归档
      友情链接