Business
Jobs
  • About Us
  • Solutions
    • Job Postings
      Post your job and receive qualified candidates in 48h.
    • Candidate Assessments
      500+ technical and psychological tests, plus anti-fraud.
    • Headhunting
      Tailor-made executive search from start to finish.
    • Payroll + EOR
      Payroll dispersal and EOR across 15+ LATAM countries.
  • Pricing
  • Jobs

0

313
Views
poner Nans en columnas que no están dentro de los números de inicio/fin para cada fila

Estoy tratando de encontrar una forma de poner un nan en columnas que no existen entre 2 valores de inicio/final en otra columna para cada fila. Digamos que tengo el siguiente marco de datos:

 df = pd.DataFrame({'39' : [1, np.nan, 3], '40' : [2, 4, 5], '41' : [3, 1, 4], '42' : [2, 5, 2], '43' : [1, 1, np.nan], 'start' : [39, 40, 41], 'end' : [41, 41, 43]}) 39 40 41 42 43 start end 0 1.0 2 3 2 1 39 41 1 NaN 4 1 5 1 40 41 2 3.0 5 4 2 3 41 43

Quiero poner un nan en las columnas numeradas que no están entre los números de columna de inicio/fin (inclusive), para obtener lo siguiente:

 39 40 41 42 43 start end 0 1.0 2.0 3 NaN NaN 39 41 1 NaN 4.0 1 NaN NaN 40 41 2 NaN NaN 4 2.0 3.0 41 43

Actualmente, la única forma en que puedo pensar en hacer esto sería iterar a través de las filas o columnas para verificar si entre el inicio y el final o no, pero sé que iterar a través de marcos de datos es una mala práctica. Podría convertir las columnas en listas e iterarlas y reasignarlas, pero me pregunto si hay una manera más eficiente de lograr esto.

Editar: debo tener en cuenta que las columnas numéricas son números de semana, por lo que es posible que superen un año (por ejemplo, 51, 52, 1, 2, 3, luego el inicio podría ser 51 y el final podría ser 1). Me pregunto si necesito hacer una lista de los números de columna para mantener antes de hacer esto, ya que usar < o > no funcionará en este caso.

Un ejemplo de esto:

 df2 = pd.DataFrame({'51' : [1, np.nan, 3], '52' : [2, 4, 5], '1' : [3, 1, 4], '2' : [2, 5, 2], '3' : [1, 1, 3], 'start' : [51, 52, 52], 'end' : [1, 2, 1]}) 51 52 1 2 3 start end 0 1.0 2 3 2 1 51 1 1 NaN 4 1 5 1 52 2 2 3.0 5 4 2 3 52 1

Producción:

 51 52 1 2 3 start end 0 1.0 2 3 NaN NaN 51 1 1 NaN 4 1 5.0 NaN 52 2 2 NaN 5 4 NaN NaN 52 1
over 4 years ago · Santiago Trujillo
3 answers
Answer question

0

Podemos hacer uso de stack y unstack aquí:

 df = df.set_index(["start", "end"]).stack() idx = df.index values = idx.get_level_values(2).astype(int) start = idx.get_level_values(0) end = idx.get_level_values(1) df.where((values >= start) & (values <= end)).unstack().reset_index()
 start end 39 40 41 42 43 0 39 41 1.0 2.0 3.0 NaN NaN 1 40 41 NaN 4.0 1.0 NaN NaN 2 41 43 NaN NaN 4.0 2.0 NaN
over 4 years ago · Santiago Trujillo Report

0

for column in ['39', '40', '41', '42', '43']: df[column].loc[(float(column) < df['start']) | (float(column) > df['end'])] = np.NaN

imprimirá:

 39 40 41 42 43 start end 0 1.0 2.0 3.0 NaN NaN 39 41 1 NaN 4.0 1.0 NaN NaN 40 41 2 NaN NaN 4.0 2.0 NaN 41 43
over 4 years ago · Santiago Trujillo Report

0

Solución numpy con comparación entre inicio y final:

 df.columns = df.columns[:-2].astype(int).tolist() + df.columns[-2:].tolist() s = df['start'].to_numpy() e = df['end'].to_numpy() cols = df.columns[:-2].to_numpy() m = (s[:, None] <= cols) & (e[:, None] >= cols) df.iloc[:, :-2] = df.iloc[:, :-2].where(m) print (df) 39 40 41 42 43 start end 0 1.0 2.0 3 NaN NaN 39 41 1 NaN 4.0 1 NaN NaN 40 41 2 NaN NaN 4 2.0 NaN 41 43

EDITAR: si no es posible, compare por valor con la suma acumulada, para e desde atrás y pruebe si 1 en ambas máscaras:

 s = df['start'].astype(str).to_numpy() e = df['end'].astype(str).to_numpy() cols = df.columns[:-2].to_numpy() m1 = np.cumsum((s[:, None] == cols), axis=1) == 1 m2 = np.cumsum((e[:, None] == cols[::-1]), axis=1)[:, ::-1] == 1 m = m1 & m2 df.iloc[:, :-2] = df.iloc[:, :-2].where(m) print (df) 51 52 1 2 3 start end 0 1.0 2 3 NaN NaN 51 1 1 NaN 4 1 5.0 NaN 52 2 2 NaN 5 4 NaN NaN 52 1
over 4 years ago · Santiago Trujillo Report
Answer question
Find remote jobs

Discover the new way to find a job!

Top jobs
Top job categories
Business
Post vacancy Pricing Sales
Legal
Terms and conditions Privacy policy
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Show me some job opportunities
There's an error!