Excel VBA macro llevar registros a otra hoja por grupo de IDs

Estoy con una macro que tiene 3 hojas (Hoja1, Hoja2, Destino). Dos columnas en cada hoja (ID, Cantidad). Empiezo siempre llevándome a hoja Destino el primer registro de hoja1 y luego en función de si la cantidad es mayor o menor a 100, me traigo otro registro de hoja1 o de hoja2 (está explicado en la segunda foto, en la primera estaría un pantallazo de hojas1 y 2). En caso de que ya no queden registros en hoja2, nos traemos de golpe todos los registros de hoja1 si quedan (siempre hay menos en hoja2 para un mismo Id). He conseguido hacerlo sin ningún problema siempre y cuando solo exista un ID. Pero no consigo sacarlo para cuando hay distintos grupos de ID (tercera foto). ¿Alguna idea? Espero que se entienda bien. Muchísimas gracias de antemano.

'empiezo trayendo el primer registros de hoja1
If Not IsEmpty(Sheets("Hoja1").Range("A2")) Then
   Sheets("Hoja1").Range("A2:D2").EntireRow.Cut Destination:=Sheets("Destino").Range("A" & Sheets("Destino").Range("A" & Rows.Count).End(xlUp).Row + 1)
   Sheets("Hoja1").Range("A2").EntireRow.Delete
'a partir de aquí empiezo con las lógicas de si es mayor o menor a 100 (foto2)
With Worksheets("Destino")
For i = 2 To .UsedRange.Rows(.UsedRange.Rows.Count).Row
 If Cells(i, "B").Value < 100 Then 
                  If Not IsEmpty(Sheets("Hoja2").Range("A2")) Then
                  Sheets("Hoja2").Range("A2:B2").EntireRow.Cut Destination:=Sheets("Destino").Range("A" & Sheets("Destino").Range("A" & Rows.Count).End(xlUp).Row + 1)
                  Sheets("Hoja2").Range("A2").EntireRow.Delete
                  end if
 else
 Sheets("Hoja1").Range("A2:B2").EntireRow.Cut Destination:=Sheets("Destino").Range("A" & Sheets("Destino").Range("A" & Rows.Count).End(xlUp).Row + 1)
Sheets("Hoja1").Range("A2").EntireRow.Delete
End if
'ahora meto la lógica de si ya no quedan más registros en hoja2 para ese ID
'que me lleve a hoja Destino el resto de Hoja1 para ese Id
 If IsEmpty(Sheets("Hoja2").Range("A2")) then
    If Not IsEmpty(Sheets("Hoja1").Range("A2")) Then
                         Sheets("Hoja1").Range("A2:B2").EntireRow.Cut Destination:=Sheets("Destino").Range("A" & Sheets("Destino").Range("A" & Rows.Count).End(xlUp).Row + 1)
                         Sheets("Hoja1").Range("A2").EntireRow.Delete
    End If
    End If            
Next
Wne with

1 Respuesta

Respuesta
1


2. Si la hoja1 y hoja2 tienen estos datos. Cuál sería el resultado en la hoja Destino:

Según tus condiciones, en la hoja Destino solamente pondría datos de la hoja1, ya que los valores de la hoja1 no son menores a 100, entonces no se debe traer nada de la hoja2.


Comenta, los 2 casos.

Hola,

Perdona. Supongo que no hice bien el ejemplo (me refiero a las cantidades). Al final el problema es que comienzo siempre con el primer registro de hoja 1, me lo llevo a destino, en función de la celda cantidad (mayor o menor a 100) tengo que traerme otro registro de hoja 1 o un registro de hoja2, así hasta que en una de las dos hojas ya no queden registros. De ser así, el resto me los llevo en orden a hoja Destino. El problema que tengo es que no encuentro el modo de que todo este proceso de inicie y ejecute hasta el final para cada grupo de IDs de forma individual. Lo intenté creando una hoja auxiliar con el listado de distintos Id y filtrando pero no termino de encontrarle solución.

Te adjunto de nuevo, hoja1, hoja2 y el cómo tendría que quedar en Destino. Espero que se entienda mejor.

Muchas gracias.

[gra cias por tu nuevo ejemplo.

Pero está mal.

En la hoja1 tienes 4 registros en el grupo 1.

En la hoja2 tienes 2 registros con el grupo 2. En total 6 registros.

Pero en la hoja Destino pusiste 8 registros.



Pero no respondiste el segundo punto.

Qué pasa si todos las cantidades en la hoja 1 son mayores a 100. Según tu regla, solamente si son menores a 100 debo traerme un registro de la hoja2.

Analiza mi ejemplo. ¿Qué datos de la hoja2 debería pasar y por qué?



Por último.

Si el registro de la hoja1 es menor, tengo que poner 2 registros. Un registro de la hoja1 y un registro de la hoja2, ¿cuál pongo primero?

En tus ejemplos no está claro, a veces pones el registro de la hoja1 y después el de la hoja2; y en otras ocasiones pones primero el registro de la hoja2 y después el de la hoja1.


Lee con atención mis comentario y anexa tus comentarios.

Podrías explicar paso a paso, pero en verdad, paso paso, cómo llegas al siguiente resultado:

Es decir:

Paso 1, inicia el grupo 2, por eso se pasa la cantidad 120 (hoja1)

Paso 2, leo el 120, como es mayor a 100, entonces paso la cantidad 20 (hoja1)

Paso 3, leo el 20, como es menor a 100, paso la cantidad 50 (hoja2)

Paso 4, ... podrías continuar con la explicación...

Dante, déjalo. En la hoja Destino a la hora de hacer el copia y pega para el ejemplo me equivoqué. Lo sabes de sobra. Y te conozco ya a estas alturas lo suficiente como para saber que no eres tonto y bien sabes lo que estoy preguntando. No lo hago a la ligera, y disculpa si no es el mejor del los ejemplos. Es un simple algoritmo. Me estrujado ya el coco lo que no está escrito y cuando vengo aquí es por ese motivo. El foro está para que aprendamos y nos ayudéis a buscar soluciones, no para que nos baciléis. Quiero la baja oficial en este foro. 

Qué pena, te diste de baja.

Leer y tratar de entender lo que necesitas es complicado. Es por eso que solicito más información. Si supiera la respuesta, la entrego de inmediato, pero cuando la macro no tiene toda la solución, si te entrego la macro incompleta, entonces tendría que estar modificando y modificando la macro; y eso representa tiempo.

Nota: Una cosa que debes tener en cuenta cuando haces una pregunta en un foro ... las personas a las que solicitas ayuda no saben absolutamente nada acerca de tus datos, absolutamente nada sobre cómo están en el libro de trabajo, absolutamente nada sobre lo que tú quieres que se haga con él y absolutamente nada sobre cómo quieres el resultado ... debes ser muy específico al describir cada una de estas áreas, en detalle, y no debes suponer que seremos capaces de "resolverlo" por nuestra cuenta. Recuerda, nos estás pidiendo ayuda ... así que ayúdanos, brindando la información que necesitamos para hacerlo, incluso si esa información te parece "obvia" (recuerda, sólo es obvia para ti porque estás familiarizado con tus datos, su diseño y el objetivo general para ellos).


Aquí tenía un avance de la macro.

Sub BarajarIds()
'Por Dante Amor
  Dim a As Variant, b As Variant, c As Variant, d As Variant
  Dim dic As Object
  Dim i As Long, j As Long, k As Long, m As Long, ini As Long, fin  As Long
  Dim enhoja2 As Boolean
  Dim ant As Variant
  '
  a = Sheets("Hoja1").Range("A2:B" & Sheets("Hoja1").Range("A" & Rows.Count).End(3).Row).Value
  b = Sheets("Hoja2").Range("A2:B" & Sheets("Hoja2").Range("A" & Rows.Count).End(3).Row).Value
  ReDim c(1 To UBound(b, 1), 1 To UBound(b, 1) * 2)
  ReDim d(1 To UBound(a, 1) + UBound(b, 1), 1 To 2)
  Set dic = CreateObject("Scripting.Dictionary")
  '
  'reconocer los datos de la hoja2
  For i = 1 To UBound(b, 1)
    If Not dic.exists(b(i, 1)) Then
      j = dic.Count + 1
      k = 1
      'ini = 1
      fin = 1
      dic(b(i, 1)) = j & "|" & k & "|" & 1 & "|" & fin
    End If
    j = Split(dic(b(i, 1)), "|")(0)
    k = Split(dic(b(i, 1)), "|")(1)
    fin = Split(dic(b(i, 1)), "|")(3)
    c(j, k) = b(i, 2)
    k = k + 1
    fin = fin + 1
    dic(b(i, 1)) = j & "|" & k & "|" & 1 & "|" & fin
  Next
  '
  For i = 1 To UBound(a, 1)
    If ant = a(i, 1) Then
      If a(i - 1, 2) < 100 Then
        j = Split(dic(a(i, 1)), "|")(0)
        k = Split(dic(a(i, 1)), "|")(1)
        ini = Split(dic(a(i, 1)), "|")(2)
        fin = Split(dic(a(i, 1)), "|")(3)
        If ini < fin Then
          m = m + 1
          d(m, 1) = a(i, 1)
          d(m, 2) = c(j, ini)
          ini = ini + 1
          dic(a(i, 1)) = j & "|" & k & "|" & ini & "|" & fin
        End If
      End If
    End If
    m = m + 1
    d(m, 1) = a(i, 1)
    d(m, 2) = a(i, 2)
    ant = a(i, 1)
  Next
  '
  Sheets("Destino").Rows("2:" & Rows. Count). ClearContents
  Sheets("Destino"). Range("A2").Resize(UBound(d, 1), 2).Value = d
End Sub

No es un simple algoritmo, como lo comentas. Tal vez alguien más pueda descifrarlo de una manera más simple.

Pero hay algunos detalles que no son explicados en tus ejemplos.

Añade tu respuesta

Haz clic para o

Más respuestas relacionadas