在Excel中使用VBA /宏重新格式化报告。将记录以单列,多行格式移动到单行,多列格式

时间:2015-10-13 16:18:43

标签: excel vba excel-vba

我正在使用一个将用户数据报告为两列的系统:列A包含字段(每条记录总共9个),列B包含相应的用户数据。

  • A列如下所示:
    1. 姓氏:
    2. 名字:
    3. 中间名:
    4. 卡号:
    5. 员工参考:
    6. 个人资料:
    7. 员工人数:
    8. 位置名称:
    9. 状态:

此报告的格式包含为每条记录重复的字段,这意味着第10行将为空白,第11行将为姓氏:第12行将为名字:等。此格式会导致报告非常冗长这很难管理。

此报告的另一个复杂因素涉及空值。具有空值的字段将从报告中排除。例如,没有位置名称的记录将完全排除“位置名称:”字段。缺少字段的结果是8行而不是正常9行的记录。由于空值,其中一些记录缺少多个字段。

我正在寻找一种优雅的方式来重新格式化此报告。具体来说,我正在寻找...... - A列中的字段成为列标题(A,B,C,D,E,F,G,H,I)。 - 列B中的数据移动到一行,与相应的字段标题对齐。

我目前正在查看的报告有3730条记录。但是,系统输出的文件为43906行(包括空行)。我想把这个报告发送到3731行(字段标题为1行+ 3730条记录)。

非常感谢您重新格式化此报告的任何帮助。

谢谢,

菲迪亚斯

以下是3条记录的一些样本数据:
•姓氏:#1

•名字:安全

•中间名:徽章

•卡号:100

•员工参考:安全

•个人详细信息:无

•员工编号:N / A

•位置名称:总部

•状态:承包商/温度

•姓氏:Doe

•名字:John

•中间名:

•卡号:101

•员工参考:

•姓氏:Deere

•名字:John

•中间名:

•卡号:102

•员工参考:

•状态:员工

1 个答案:

答案 0 :(得分:0)

试试这个。

将以下例程放入标准代码模块中:

Sub pheidias()
    Dim c&, i&, t, v, w
    With ActiveSheet.[a1]
        v = .Resize(.Item(.Parent.Rows.Count).End(xlUp).Row, 2)
    End With
    ReDim w(1 To UBound(v), 1 To 9)
    t = Split(".Last Name.First Name.Middle Name.Card Number.Employee Ref.Personal Details.Associate Number.Location Name.Status.", ".")
    For i = 1 To 9
        w(1, i) = t(i)
    Next
    c = 2
    For i = 1 To UBound(v)
        If Len(v(i, 1)) Then
            w(c, (InStr("lafimicaempeaslost", LCase$(Left$(v(i, 1), 2))) - 1) / 2 + 1) = v(i, 2)
        Else
            c = c + 1
        End If
    Next
    [e1].Resize(UBound(w), UBound(w, 2)) = w
End Sub

注意:此例程假设数据从单元格A1开始,并且只有一个空白行分隔每个源报表组。

注意:可以在最后一行编辑输出的位置。输出报告的左上角当前默认为单元格E1。

<强>更新

也试试这个。这两个版本实际上是相同的,但下面的版本可能更容易阅读...

Sub pheidias()
    Dim c&, i&, v, w

    With ActiveSheet.[a1]
        v = .Resize(.Item(.Parent.Rows.Count).End(xlUp).Row, 2)
    End With

    ReDim w(1 To UBound(v), 1 To 9)

    w(1, 1) = "Last Name"
    w(1, 2) = "First Name"
    w(1, 3) = "Middle Name"
    w(1, 4) = "Card Number"
    w(1, 5) = "Employee Ref"
    w(1, 6) = "Personal Details"
    w(1, 7) = "Associate Number"
    w(1, 8) = "Location Name"
    w(1, 9) = "Status"

    c = 2
    For i = 1 To UBound(v)
        If Len(v(i, 1)) Then
            Select Case LCase$(Left$(v(i, 1), 2))
                Case "la":  w(c, 1) = v(i, 2)
                Case "fi":  w(c, 2) = v(i, 2)
                Case "mi":  w(c, 3) = v(i, 2)
                Case "ca":  w(c, 4) = v(i, 2)
                Case "em":  w(c, 5) = v(i, 2)
                Case "pe":  w(c, 6) = v(i, 2)
                Case "as":  w(c, 7) = v(i, 2)
                Case "lo":  w(c, 8) = v(i, 2)
                Case "st":  w(c, 9) = v(i, 2)
            End Select
        Else
            c = c + 1
        End If
    Next

    [e1].Resize(UBound(w), UBound(w, 2)) = w

End Sub