Фрейм данных Pandas лучшая подгонка строки

#python #pandas #dataframe #seaborn #curve-fitting

Вопрос:

Привет, у меня есть следующий набор данных:

 A = [1,10,23,45,24,25,55,67,73,26,13,96,53,23,24,43,90, 49], 
B = [24,23,29, BW,49,59,72, BW,9,183,17,12,2,49,BW,479,18,BW]
 

Я хочу поместить прямые линии между ‘BW’ со столбцом по оси x и сохранить значения наклона в новом столбце C.
То есть наклон 1 получается путем использования [1,10,23] в качестве значений x и [24,23,29] в качестве значений y. Наклон 2 получается с использованием [24,25,55] в качестве значений x и [49,59,72] в качестве значений y. Это продолжается до конца фрейма данных.
Ожидаемый результат будет:

 C = [slope1, np.nan, np.nan, BW, slope2, np.nan, np.nan, BW, slope3,np.nan, np.nan,np.nan,np.nan,np.nan, BW, slope4, np.nan, BW]
 

Кроме того, есть ли способ, которым я могу показать эти линии на графике? Я новичок в этом деле и понятия не имею. Любая помощь будет очень признательна.

Комментарии:

1. Что вы подразумеваете под «между» BW? Кроме того, вы можете перефразировать свой вопрос, чтобы его было легче понять.

2. Я имел в виду значения в столбцах B между появлением определенного текста ‘BW’

Ответ №1:

Вы можете определить местоположения ‘BW’, а затем разделить свои массивы по этим индексам. Вот пример того, как вы могли бы это сделать:

 from pprint import pprint

import matplotlib.colors as mcolors
import matplotlib.pyplot as plt
import numpy as np

colors = list(mcolors.TABLEAU_COLORS.values())

A = [1, 10, 23, 45, 24, 25, 55, 67, 73, 26, 13, 96, 53, 23, 24, 43, 90, 49]
B = [24, 23, 29, 'BW', 49, 59, 72, 'BW', 9,
     183, 17, 12, 2, 49, 'BW', 479, 18, 'BW']


index = [k for k, value in enumerate(B) if value == 'BW']
index = [-1]   index   [len(B)]

slopes = []

for k in range(len(index)-1):
    x = A[index[k] 1:index[k 1]]
    y = B[index[k] 1:index[k 1]]

    if len(x) == 0:
        continue

    [slope, offset] = np.polyfit(x, y, 1)
    slopes.append(slope)

    reg_x = np.linspace(min(x), max(x), 10)
    reg_y = slope*reg_x   offset

    plt.plot(x, y, 'o', color=colors[k], label=f'Group {k}')
    plt.plot(reg_x, reg_y, color=colors[k])

pprint(slopes)

plt.legend()
plt.show()
 

В качестве вектора наклона результат

 [0.24386920980926416,
 0.5977443609022566,
 -0.9183274470232099,
 -9.808510638297868]
 

И сюжет:
примерный график

Возможно, это не самый элегантный или питонический способ решения этой проблемы, но он выполняет свою работу

Комментарии:

1. Возможно ли иметь значение соответствия (R2) в каждом случае?

2. да, конечно. Внутри цикла данные x и y уже разделены на куски, поэтому вы можете использовать функцию scipy для линейной регрессии scipy.stats.linregress , которая уже возвращает коэффициент корреляции.

3. Большое вам спасибо. Это решило для меня проблему длиной в два месяца.