简体   繁体   English

Excel Pivot表-具有日期和另一列的格式设置和分组列

[英]Excel Pivot Table - Formatting and Grouping Columns with Dates and Another Column

I have worked with basic pivot tables for a few years, however I am getting stuck on something that I think should be fairly simple to solve (ugh). 我使用基本数据透视表已经有几年了,但是我陷入了一些我认为应该很容易解决的问题。

I would like to format my pivot table in a specific way. 我想以特定方式格式化我的数据透视表。

For example, just say I am using the following data: 例如,仅说我正在使用以下数据:

Client Name Stage   Amount Paid  Date Paid
Client A    Start    $70,000     1/10/2015
Client A    Middle   $50,000     1/11/2015
Client A    End      $30,000     1/12/2015
Client B    Start    $50,000     5/11/2015
Client B    Middle   $30,000     5/11/2015
Client B    End      $50,000     5/12/2015
Client C    Start    $10,000     10/12/2015
Client C    Middle   $20,000     20/12/2015
Client C    End      $30,000     30/12/2015

I would like to arrange the pivot table so that it looks like this: 我想安排数据透视表,使其看起来像这样:

Table Example with Correct Formatting 具有正确格式的表格示例

The only way I can almost get it to work is if it looks like this: 我几乎可以正常使用的唯一方法是,它看起来像这样:

PivotTable Example - Not correct formatting 数据透视表示例-格式不正确

I really need the formatting to be exactly like picture one. 我确实需要将其格式设置为与图片一模一样。

Thanks for any help you may be able to provide. 感谢您提供的任何帮助。

Answers in excel steps or in VBA code would be awesome :) excel步骤或VBA代码中的答案都很棒:)

I think you cannot have exactly the output that you want with a pivote table. 我认为您无法通过数据透视表确切获得所需的输出。 So i wrote a code which create first a pivot table as close as you want. 所以我写了一个代码,该代码首先根据需要创建一个数据透视表。 And then other macro which will create the exact format table as you put in the picture. 然后是另一个宏,它将在您放入图片时创建确切的格式表。

1) However you have (it could be easily automated) to replace in your row data: 1)但是,您可以(可以很容易地使其自动化)替换行数据:

Start by 1 Start 1 Start

Middle by 2 Middle2

End by 3 3 End

And your row data tittles should be in Sheet1 and start cell A1 并且您的行数据标题应位于Sheet1并开始于Sheet1A1

Main sub to call all codes: (all codes have to be in the same module. How hope it can help you. 用来调用所有代码的主要子代码:(所有代码必须在同一模块中。希望它能为您提供多大的希望。

Sub main()

Call PivotTable
Call FinalTable
Call DeleteRow
Call FormatTable

End Sub

Here is the first code that create the pivot table: 这是创建数据透视表的第一个代码:

Sub PivotTable()

Dim PTCache As PivotCache
Dim PT As PivotTable

'1.CREATE DATA STORAGE UNIT
Set PTCache = ActiveWorkbook.PivotCaches.Create( _
SourceType:=xlDatabase, _
SourceData:=Range("A1").CurrentRegion)

'2. ADD WORKSHEET
Worksheets.Add
ActiveSheet.Name = "PivotTable1"

'3.CREATE PIVOT TABLE N*1
Set PT = ActiveSheet.PivotTables.Add( _
PivotCache:=PTCache, _
TableDestination:=Range("A3"))

'4. ENUMERATE PREFERENCES FOR PIVOTE TABLE
With PT
    .PivotFields("Client Name").Orientation = xlRowField
    .PivotFields("Amount Paid").Orientation = xlRowField
    .RowAxisLayout xlTabularRow
End With

'MODIFYING DATA FIELD CALCULATION
With PT.PivotFields("Client Name")
      .Subtotals(1) = False
End With

With PT.PivotFields("Date Paid")
 .Orientation = xlColumnField
    .Caption = " Date Paid"
End With

With PT.PivotFields("Stage")
  .Orientation = xlDataField
    .Caption = " Stage"
    .NumberFormat = "[=1]""Start"";[>2]""End"";""Middle"""
End With

With PT.PivotFields("Amount Paid")
 .Orientation = xlDataField
   .Function = xlSum
    .Caption = " Amount Paid"
End With

Range("C4").Select
Selection.Group Start:=True, End:=True, Periods:=Array(False, False, False, _
        False, True, False, False)

PT.DisplayErrorString = False
PT.HasAutoFormat = False

PT.PivotSelect "", xlDataAndLabel, True
Selection.Copy
Worksheets.Add
ActiveSheet.Name = "FinalTable"
Range("A1").PasteSpecial xlPasteValuesAndNumberFormats

Rows(1).Delete
Columns("B").Delete
Columns("I").Delete
Columns("H").Delete


End Sub

To format: 格式化:

Sub FinalTable()
Dim Nextcell As Double
Dim j As Integer

    Lastrow = Sheets("FinalTable").Range("A1").SpecialCells(xlCellTypeLastCell).Row

i = 3
Do Until i = Lastrow

    NextProcess i, Nextcell, Lastrow, j
        For c = 2 To 7

        If j = Lastrow Then Exit Do


    If IsEmpty(Cells(i, c)) Then

        For j = Nextcell - 1 To i Step -1

            If Not IsEmpty(Cells(j, c)) And Not IsEmpty(Cells(j - 1, c)) Then
                 Range(Cells(j, c), Cells(j - 1, c)).Copy Cells(i, c)
                 Range(Cells(j, c), Cells(j - 1, c)).ClearContents
                Exit For
            End If

            If Not IsEmpty(Cells(j, c)) Then
                 Cells(j, c).Copy Cells(i, c)
                 Cells(j, c).ClearContents
                Exit For
            End If

             If Not IsEmpty(Cells(j - 1, c)) Then
                 Cells(j - 1, c).Copy Cells(i, c)
                 Cells(j - 1, c).ClearContents
                Exit For
            End If

        Next j

    End If

    Next c

StepB = Nextcell - i
i = StepB + i

Loop

i = 2

Do

    If Application.WorksheetFunction.CountA(Rows(i)) = 0 Then
        Rows(i).Delete
        i = i - 1

    End If

Lastrow = Sheets("FinalTable").Range("A" & Rows.Count).End(xlUp).Row

i = 1 + i
Loop Until i = Lastrow


End Sub

Code to delete the empty rows in your Final Table 代码删除最终表中的空行

Sub DeleteRow()

Dim Lastrow As Long
Dim i As Integer

Lastrow = Sheets("FinalTable").Range("A" & Rows.Count).End(xlUp).Row

i = 2

Do

    If Application.WorksheetFunction.CountA(Rows(i)) = 0 Then
        Rows(i).Delete
        i = i - 1

    End If

Lastrow = Sheets("FinalTable").Range("A" & Rows.Count).End(xlUp).Row

i = 1 + i
Loop Until i = Lastrow

End Sub

Code to put border in your final table: 将边框放在最终表中的代码:

Sub FormatTable()

Dim Nextcell As Double
Dim j As Integer

Lastrow = Sheets("FinalTable").Range("G" & Rows.Count).End(xlUp).Row

For i = 2 To Lastrow

    If Not IsEmpty(Cells(i, 1)) Then

        If Not IsEmpty(Cells(i + 1, 1)) Then

                Range(Cells(i, 1), Cells(i, 7)).BorderAround

        ElseIf Not IsEmpty(Cells(i + 2, 1)) Then

                NextProcess i, Nextcell, Lastrow, j

                Range(Cells(i, 1), Cells(Nextcell - 1, 7)).BorderAround

        Else

        Range(Cells(i, 1), Cells(Lastrow, 7)).BorderAround

        End If
    End If
    Range(Cells(1, 2), Cells(Lastrow, 3)).BorderAround
    Range(Cells(1, 4), Cells(Lastrow, 5)).BorderAround
    Range(Cells(1, 6), Cells(Lastrow, 7)).BorderAround

Next i


End Sub

The subroutine to find the next client name: 查找下一个客户端名称的子例程:

Sub NextProcess(ByVal i As Integer, ByRef Nextcell As Double, ByVal Lastrow As Long, ByRef j As Integer)

Dim Found As Boolean
'Dim j As Integer

Found = False
j = i + 1

Do Until Found = True Or Lastrow = j

        If Not IsEmpty(Range("A" & j).Value) Then

                Nextcell = Cells(j, 1).Row
                Found = True

        End If

j = j + 1
Loop

End Sub

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM