• Privacywetgeving
    Het is bij Helpmij.nl niet toegestaan om persoonsgegevens in een voorbeeld te plaatsen. Alle voorbeelden die persoonsgegevens bevatten zullen zonder opgaaf van reden verwijderd worden. In de vraag zal specifiek vermeld moeten worden dat het om fictieve namen gaat.

Macro aanpassen van aantal regels optellen naar som toepassen

Status
Niet open voor verdere reacties.

Niek91

Gebruiker
Lid geworden
22 feb 2012
Berichten
77
Goedemiddag,

Zouden jullie mij kunnen helpen?
Met behulp van dit forum heb ik een tijd geleden bijgevoegd bestand in elkaar gedraaid. Hier zit een macro in die op persoonsniveau het aantal regels optelt.
Nu wil ik met tabblad 'trucken en invakken' niks wijzigen. maar bij de andere tabbladen wel.
Daar wordt nu in tabblad 'productiviteit' onder 'aantal scans' het aantal regels opgeteld per persoon.
maar bij die andere 3 onderwerpen wil ik graag het totaal aan stuks bij elkaar optellen dmv 'som'. onder het kopje 'aantal stuks'. Daar wordt nu ook het aantal regels opgeteld.
Maar zover ik het kan zien moet dan heel de macro op zijn kop.


Code:
Sub HetLoopje()
Productiviteit Sheets("orderpicken").Range("A1").CurrentRegion, 21, 17, Range("A3:G32")
Productiviteit Sheets("inpakken").Range("A1").CurrentRegion, 1, 6, Range("A36:G65")
Productiviteit Sheets("Trucken-Invakken").Range("A1").CurrentRegion, 14, 9, Range("A69:G100")
Productiviteit Sheets("AG sorteren").Range("A1").CurrentRegion, 14, 9, Range("A104:G120")

End Sub


Sub Productiviteit(MijnGegevens As Range, KolNaam As Integer, KolTijd As Integer, Uitvoer As Range)
  Dim a, i&, it, dTijd As Double, splits, Pers$
  a = MijnGegevens.Value 'inlezen gegevens
  
  With CreateObject("System.Collections.Arraylist") 'om straks oplopend te sorteren
    For i = 2 To UBound(a)
      Select Case VarType(a(i, KolTijd))                        'kijk naar je tijd
        Case vbString                                      'is het een string
          splits = Split(Replace(a(i, KolTijd), "-", " "))      'vervang "-" door een spatie en verknip op die spaties
          If UBound(splits) = 3 Then                       '4 knipsels
            a(i, KolTijd) = DateSerial(splits(2), splits(1), splits(0)) + TimeValue(splits(3))  'je tijdstip met datum
          Else
            a(i, KolTijd) = TimeValue(splits(0))                'je tijdstip
          End If
        Case vbDate, vbDouble                                       'het is al een date of een double
        Case Else: MsgBox "??? vbDate"
      End Select
      dTijd = a(i, KolTijd)                                     'maak er een double van
      .Add Join$(Array(Format(dTijd, "00000.0000000"), a(i, KolNaam)), Chr(2)) 'naar arraylist schrijven
    Next
    .Sort 'sorteren
    a = .toarray() 'naar array schrijven
    If Not IsArray(a) Then MsgBox "geen gegevens", vbCritical: Exit Sub
  End With

  With CreateObject("scripting.dictionary")
    .comparemode = 1
    For i = LBound(a) To UBound(a)
      splits = Split(a(i), Chr(2))
      dTijd = splits(0)
      Pers = splits(1)
      it = .Item(Pers)                                     'kijk naar die persoon in de dictionary
      If VarType(it) = vbEmpty Then                        'persoon bestond nog niet in dictionary
        .Item(Pers) = Array(Pers, dTijd, dTijd, 0, 1, 0, 0)  'array met naam, Start, Einde, onderbrekingen,aantal scans, gewerkte tijd,Productiviteit
      Else
        If dTijd - it(2) > TimeSerial(0, 30, 0) Then it(3) = it(3) + dTijd - it(2)  'tijd tov vorig gegeven bijtellen indien tussentijd>30 min
        it(4) = it(4) + 1                                  'scan + 1
        it(2) = dTijd                                      'laatste tijd
        .Item(Pers) = it                               'terugschrijven naar dictionary
      End If
    Next
    If .Count = 1 Then .Item("") = Array("", "", "", "", "", "", "")

    a = ""
    If .Count Then
      a = Application.Transpose(Application.Transpose(.items))  'uitlezen items van dictionary
      For i = 1 To UBound(a)                               'alle personen aflopen
        If Len(a(i, 1)) Then
          a(i, 6) = a(i, 3) - a(i, 2) - a(i, 4)            'gewerkte tijd
          If a(i, 5) > 1 Then a(i, 7) = a(i, 5) / (a(i, 6) + 0.0000000001) / 24 'productiviteit
        End If
      Next
    End If
  End With

  With Uitvoer            'naar hier schrijven
    .ClearContents
    If IsArray(a) Then .Resize(WorksheetFunction.Min(.Rows.Count, UBound(a)), UBound(a, 2)).Value = a  'de gegevens
  End With

End Sub
iemand mij hiermee helpen?
 
Laatst bewerkt:
Ja sorry, dat was de bedoeling. Maar bestand was te groot. Ik heb nu alleen de code erin geplakt. Is dat voldoende of is een voorbeeldbestand essentieel?
 
Is wel fijn om mee te testen.
Anders moet ik of een andere helper toch zelf iets maken.
 
Is er iemand die me hiermee misschien verder kan helpen?
Alvast bedankt.
 
Ik denk zo:
Code:
Option Explicit

Sub HetLoopje()
    Productiviteit Sheets("Orderpicken").Range("A1").CurrentRegion, 21, 17, 15, Range("A3:G32")
    Productiviteit Sheets("inpakken").Range("A1").CurrentRegion, 1, 6, [COLOR="#FF0000"]0[/COLOR], Range("A36:G65")
    Productiviteit Sheets("Trucken-Invakken").Range("A1").CurrentRegion, 14, 9, 0, Range("A69:G100")
    Productiviteit Sheets("AG sorteren").Range("A1").CurrentRegion, 14, 9, [COLOR="#FF0000"]0[/COLOR], Range("A104:G120")
End Sub

Sub Productiviteit(MijnGegevens As Range, KolNaam As Integer, KolTijd As Integer, KolStuks As Integer, Uitvoer As Range)
    Dim A, I&, It, dTijd As Double, Splits, Pers$
    A = MijnGegevens.Value 'inlezen gegevens
  
    With CreateObject("System.Collections.Arraylist") 'om straks oplopend te sorteren
        For I = 2 To UBound(A)
            Select Case VarType(A(I, KolTijd))                        'kijk naar je tijd
                Case vbString                                      'is het een string
                    Splits = Split(Replace(A(I, KolTijd), "-", " "))      'vervang "-" door een spatie en verknip op die spaties
                    If UBound(Splits) = 3 Then                       '4 knipsels
                        A(I, KolTijd) = DateSerial(Splits(2), Splits(1), Splits(0)) + TimeValue(Splits(3))  'je tijdstip met datum
                    Else
                        A(I, KolTijd) = TimeValue(Splits(0))                'je tijdstip
                    End If
                Case vbDate, vbDouble                                       'het is al een date of een double
                Case Else: MsgBox "??? vbDate"
            End Select
            dTijd = A(I, KolTijd)                                     'maak er een double van
            .Add Join$(Array(Format(dTijd, "00000.0000000"), A(I, KolNaam)), Chr(2)) 'naar arraylist schrijven
        Next
        .Sort 'sorteren
        A = .toarray() 'naar array schrijven
        If Not IsArray(A) Then MsgBox "geen gegevens", vbCritical: Exit Sub
    End With

    With CreateObject("Scripting.Dictionary")
        .CompareMode = 1
        For I = LBound(A) To UBound(A)
            Splits = Split(A(I), Chr(2))
            dTijd = Splits(0)
            Pers = Splits(1)
            It = .Item(Pers)                                     'kijk naar die persoon in de dictionary
            If VarType(It) = vbEmpty Then                        'persoon bestond nog niet in dictionary
                .Item(Pers) = Array(Pers, dTijd, dTijd, 0, 1, 0, 0)  'array met naam, Start, Einde, onderbrekingen,aantal scans, gewerkte tijd,Productiviteit
            Else
                If dTijd - It(2) > TimeSerial(0, 30, 0) Then It(3) = It(3) + dTijd - It(2)  'tijd tov vorig gegeven bijtellen indien tussentijd>30 min
                It(4) = It(4) + 1 'scan + 1
                It(2) = dTijd                                      'laatste tijd
                .Item(Pers) = It                               'terugschrijven naar dictionary
            End If
        Next
        If .Count = 1 Then .Item("") = Array("", "", "", "", "", "", "")

        A = ""
        If .Count Then
            A = Application.Index(.items, 0) 'uitlezen items van dictionary
            For I = 1 To UBound(A)                               'alle personen aflopen
                [COLOR="#FF0000"]If MijnGegevens.Parent.Name <> "Trucken-Invakken" Then A(I, 5) = _
                    Application.SumIf(MijnGegevens.Columns(KolNaam), A(I, 1), MijnGegevens.Columns(KolStuks))[/COLOR]
                If Len(A(I, 1)) Then
                    A(I, 6) = A(I, 3) - A(I, 2) - A(I, 4)            'gewerkte tijd
                    If A(I, 5) > 1 Then A(I, 7) = A(I, 5) / (A(I, 6) + 0.0000000001) / 24 'productiviteit
                End If
            Next
        End If
    End With

    With Uitvoer            'naar hier schrijven
        .ClearContents
        If IsArray(A) Then .Resize(WorksheetFunction.Min(.Rows.Count, UBound(A)), UBound(A, 2)).Value = A  'de gegevens
    End With
End Sub

De routine "Productiviteit" is uitgebreid met een argument "KolStuks as integer". De roodgekleurde nullen dien je te vervangen door het kolomnummer "Stuks" in het betreffende werkblad. De 0 bij werkblad "Trucken-Invakken" kun je laten staan.
 
Laatst bewerkt:
Dank! Dat ziet er al goed uit.
Alleen ik ben wat aan het testen maar bij 'Orderpicken' en 'trucken-invakken' krijg ik bij het aantal scans alleen maar 0.
Dus bij orderpicken telt die niet het aantal stuks op. En bij trucken-invakken niet het aantal regels.

Ik heb de juiste kolommen ingevuld zoals je hebt aangegeven.
 
Kun je een uitgebreider voorbeeld plaatsen?
Dus met alle 5 de werkbladen erin en bovendien voorbeeldregels per werkblad.
 
Hoi Tim,

Ik heb echt van alles geprobeerd maar ik krijg het bestand niet klein genoeg om toe te voegen als bijlage.:(
Tabblad 1= orderpicken met in kolom o stuks/q tijd/u gebruiker
Tabblad 2= inpakken(Die werkt met de macro)
Tabblad 3= Trucken-invakken met in kolom i tijd/n gebruiker/r stuks
Tabblad 4= Ag sorteren(Die werkt ook met de macro)
Tabblad 5= resultaat van de macro vanuit bovenstaande.

Heb je hier iets aan?
 
Ik heb echt een goed voorbeeld nodig.
Probeer op te slaan als binair bestand (.xlsb). 10 voorbeeldregels per werkblad is genoeg. Als het dan nog niet lukt, gebruik dan maar dropbox of zoiets.
 
Kolom O van werkblad "Orderpicken" ziet eruit als getallen maar is in feite opgemaakt als tekst. Dan kan Excel/VBA er niet mee rekenen.
Maak de cellen op als getal en voer de waarden in die kolom opnieuw in.
Voorts heb ik de routine nog iets aangepast. De rode 0 is verplicht:

Code:
Option Explicit

Sub HetLoopje()
    Productiviteit Sheets("Orderpicken").Range("A1").CurrentRegion, 21, 17, 15, Range("A3:G32")
    Productiviteit Sheets("inpakken").Range("A1").CurrentRegion, 1, 6, 9, Range("A36:G65")
    Productiviteit Sheets("Trucken-Invakken").Range("A1").CurrentRegion, 14, 9, [COLOR="#FF0000"][B]0[/B][/COLOR], Range("A69:G100")
    Productiviteit Sheets("AG sorteren").Range("A1").CurrentRegion, 14, 9, 18, Range("A104:G120")
End Sub

Sub Productiviteit(MijnGegevens As Range, KolNaam As Integer, KolTijd As Integer, KolStuks As Integer, Uitvoer As Range)
    Dim A, I&, It, dTijd As Double, Splits, Pers$
    A = MijnGegevens.Value 'inlezen gegevens
  
    With CreateObject("System.Collections.Arraylist") 'om straks oplopend te sorteren
        For I = 2 To UBound(A)
            Select Case VarType(A(I, KolTijd))                        'kijk naar je tijd
                Case vbString                                      'is het een string
                    Splits = Split(Replace(A(I, KolTijd), "-", " "))      'vervang "-" door een spatie en verknip op die spaties
                    If UBound(Splits) = 3 Then                       '4 knipsels
                        A(I, KolTijd) = DateSerial(Splits(2), Splits(1), Splits(0)) + TimeValue(Splits(3))  'je tijdstip met datum
                    Else
                        A(I, KolTijd) = TimeValue(Splits(0))                'je tijdstip
                    End If
                Case vbDate, vbDouble                                       'het is al een date of een double
                Case Else: MsgBox "??? vbDate"
            End Select
            dTijd = A(I, KolTijd)                                     'maak er een double van
            .Add Join$(Array(Format(dTijd, "00000.0000000"), A(I, KolNaam)), Chr(2)) 'naar arraylist schrijven
        Next
        .Sort 'sorteren
        A = .toarray() 'naar array schrijven
        If Not IsArray(A) Then MsgBox "geen gegevens", vbCritical: Exit Sub
    End With

    With CreateObject("Scripting.Dictionary")
        .CompareMode = 1
        For I = LBound(A) To UBound(A)
            Splits = Split(A(I), Chr(2))
            dTijd = Splits(0)
            Pers = Splits(1)
            It = .Item(Pers)                                     'kijk naar die persoon in de dictionary
            If VarType(It) = vbEmpty Then                        'persoon bestond nog niet in dictionary
                .Item(Pers) = Array(Pers, dTijd, dTijd, 0, 1, 0, 0)  'array met naam, Start, Einde, onderbrekingen,aantal scans, gewerkte tijd,Productiviteit
            Else
                If dTijd - It(2) > TimeSerial(0, 30, 0) Then It(3) = It(3) + dTijd - It(2)  'tijd tov vorig gegeven bijtellen indien tussentijd>30 min
                It(4) = It(4) + 1 'scan + 1
                It(2) = dTijd                                      'laatste tijd
                .Item(Pers) = It                               'terugschrijven naar dictionary
            End If
        Next
        If .Count = 1 Then .Item("") = Array("", "", "", "", "", "", "")

        A = ""
        If .Count Then
            A = Application.Index(.items, 0) 'uitlezen items van dictionary
            For I = 1 To UBound(A)                               'alle personen aflopen
                If KolStuks > 0 Then A(I, 5) = _
                    Application.SumIf(MijnGegevens.Columns(KolNaam), A(I, 1), MijnGegevens.Columns(KolStuks))
                If Len(A(I, 1)) Then
                    A(I, 6) = A(I, 3) - A(I, 2) - A(I, 4)            'gewerkte tijd
                    If A(I, 5) > 1 Then A(I, 7) = A(I, 5) / (A(I, 6) + 0.0000000001) / 24 'productiviteit
                End If
            Next
        End If
    End With

    With Uitvoer            'naar hier schrijven
        .ClearContents
        If IsArray(A) Then .Resize(WorksheetFunction.Min(.Rows.Count, UBound(A)), UBound(A, 2)).Value = A  'de gegevens
    End With
End Sub
 

Bijlagen

Laatst bewerkt:
Status
Niet open voor verdere reacties.
Terug
Bovenaan Onderaan