รับรายการจากหัวคอลัมน์ DataFrame แพนด้า


1013

ฉันต้องการรับรายการส่วนหัวคอลัมน์จาก DataFrame แพนด้า DataFrame จะมาจากการป้อนข้อมูลของผู้ใช้ดังนั้นฉันจะไม่ทราบจำนวนคอลัมน์ที่จะมีหรือสิ่งที่พวกเขาจะถูกเรียก

ตัวอย่างเช่นถ้าฉันได้รับ DataFrame เช่นนี้:

>>> my_dataframe
    y  gdp  cap
0   1    2    5
1   2    3    9
2   8    7    2
3   3    4    7
4   6    7    7
5   4    8    3
6   8    2    8
7   9    9   10
8   6    6    4
9  10   10    7

ฉันต้องการรับรายการแบบนี้:

>>> header_list
['y', 'gdp', 'cap']

คำตอบ:


1645

คุณสามารถรับค่าเป็นรายการโดยทำ:

list(my_dataframe.columns.values)

นอกจากนี้คุณสามารถใช้: (ดังแสดงในคำตอบของ Ed Chum ):

list(my_dataframe)

42
ทำไมเอกสารนี้ไม่ได้columnsมีคุณสมบัติเป็น?
Tjorriemorrie

@Jorriemorrie: ฉันไม่แน่ใจว่ามันอาจจะเกี่ยวข้องกับวิธีที่พวกเขาสร้างเอกสารของพวกเขาโดยอัตโนมัติ มันถูกกล่าวถึงในที่อื่น ๆ แม้ว่า: pandas.pydata.org/pandas-docs/stable/ …
Simeon Visser

8
ฉันคาดหวังอะไรแบบdf.column_names()นี้ คำตอบนี้ยังคงถูกหรือล้าสมัย?
alvas

1
@alvas มีวิธีอื่น ๆ อีกมากมายที่จะทำ (ดูคำตอบอื่น ๆ ในหน้านี้) แต่เท่าที่ฉันรู้ว่าไม่มีวิธีใน dataframe โดยตรงเพื่อสร้างรายการ
Simeon Visser

19
สิ่งสำคัญคือจะรักษาลำดับของคอลัมน์
WindChimes

402

มีวิธีการในตัวซึ่งเป็นสิ่งที่มีประสิทธิภาพมากที่สุด:

my_dataframe.columns.values.tolist()

.columnsส่งคืนดัชนี.columns.valuesส่งกลับอาร์เรย์และมีฟังก์ชั่นผู้ช่วย.tolistเพื่อกลับรายการ

หากประสิทธิภาพไม่สำคัญเท่ากับคุณIndexวัตถุจะกำหนด.tolist()วิธีการที่คุณสามารถโทรได้โดยตรง:

my_dataframe.columns.tolist()

ความแตกต่างของประสิทธิภาพชัดเจน:

%timeit df.columns.tolist()
16.7 µs ± 317 ns per loop (mean ± std. dev. of 7 runs, 100000 loops each)

%timeit df.columns.values.tolist()
1.24 µs ± 12.3 ns per loop (mean ± std. dev. of 7 runs, 1000000 loops each)

สำหรับผู้ที่เกลียดการพิมพ์คุณก็สามารถโทรlistได้ที่dfเป็นดังนั้น:

list(df)

4
ไม่ได้ลงคะแนน แต่ต้องการอธิบาย: อย่าพึ่งพารายละเอียดการใช้งานให้ใช้ "ส่วนต่อประสานสาธารณะ" ของ DataFrame คิดเกี่ยวกับความงามของ df.keys ()
Sascha Gottfried

3
@SaschaGottfried การดำเนินงานของDataFrameiterable ไม่ได้เปลี่ยนแปลงตั้งแต่วันหนึ่ง: pandas.pydata.org/pandas-docs/stable/basics.html#iteration การทำซ้ำที่ส่งคืนจาก DataFrame เป็นคอลัมน์เสมอดังนั้นการทำเช่นนี้for col in df:ควรจะทำงานเหมือนเดิมทุกครั้งเว้นแต่ผู้พัฒนาจะมีการล่มสลายเช่นlist(df)นั้นและควรเป็นวิธีที่ถูกต้อง โปรดทราบว่าdf.keys()กำลังเรียกใช้การใช้งานภายในของโครงสร้างคล้าย dict ที่ส่งคืนคีย์ซึ่งเป็นคอลัมน์ downvotes อธิบายไม่ได้เป็นหลักประกันความเสียหายที่จะคาดหวังในดังนั้นจึงไม่ต้องกังวล
EdChum

ฉันกำลังอ้างถึงรายละเอียดการใช้งานของcolumnsคุณลักษณะ หนึ่งชั่วโมงก่อนฉันอ่านเกี่ยวกับ Law of Demeter ที่ส่งเสริมว่าผู้โทรไม่ควรขึ้นอยู่กับการนำทางโมเดลวัตถุภายใน list(df)การแปลงประเภทที่ไม่ชัดเจน ผลข้างเคียงที่น่าสังเกต: การดำเนินการเวลาและหน่วยความจำที่เพิ่มขึ้นการบริโภคที่มีขนาด dataframe df.keys()วิธีการเป็นส่วนหนึ่งของธรรมชาติ Dict DataFrameเหมือนของ ความจริงที่น่าสังเกต: เวลาดำเนินการสำหรับdf.keys()ค่อนข้างคงที่โดยไม่คำนึงถึงขนาดของดาต้าเฟรม - ส่วนหนึ่งของความรับผิดชอบของนักพัฒนานุ่น
Sascha Gottfried

1
@SaschaGottfried ฉันสามารถเพิ่มสิ่งนี้ลงในคำตอบและเครดิตที่คุณเห็นเนื่องจากไม่มีใครได้รวมสิ่งนี้ไว้
EdChum

1
ฉันเห็นคุณค่าของคำตอบที่ได้รับรวมถึงความคิดเห็นโดยไม่จำเป็นต้องเปลี่ยนแปลงอะไรเลย
Sascha Gottfried

89

ทำการทดสอบอย่างรวดเร็วและบางทีการใช้เวอร์ชันในตัวที่ไม่น่าแปลกใจdataframe.columns.values.tolist()ก็เป็นวิธีที่เร็วที่สุด:

In [1]: %timeit [column for column in df]
1000 loops, best of 3: 81.6 µs per loop

In [2]: %timeit df.columns.values.tolist()
10000 loops, best of 3: 16.1 µs per loop

In [3]: %timeit list(df)
10000 loops, best of 3: 44.9 µs per loop

In [4]: % timeit list(df.columns.values)
10000 loops, best of 3: 38.4 µs per loop

(ฉันยังชอบอยู่เหมือนlist(dataframe)เดิมดังนั้นขอบคุณ EdChum!)


47

มันง่ายยิ่งขึ้น (โดย pandas 0.16.0):

df.columns.tolist()

จะให้ชื่อคอลัมน์ในรายการที่ดี


37
>>> list(my_dataframe)
['y', 'gdp', 'cap']

ในการแสดงรายการคอลัมน์ของ dataframe ขณะอยู่ในโหมดดีบักเกอร์ให้ใช้ list comprehension:

>>> [c for c in my_dataframe]
['y', 'gdp', 'cap']

โดยวิธีการที่คุณจะได้รับรายการเรียงโดยใช้sorted:

>>> sorted(my_dataframe)
['cap', 'gdp', 'y']

จะใช้list(df)งานได้เฉพาะกับ dataframes อัตโนมัติหรือไม่ หรือมันใช้งานได้กับดาต้าเฟรมทั้งหมด
alvas

2
ควรทำงานให้กับทุกคน เมื่อคุณอยู่ในการดีบัก [c for c in df]แต่คุณจำเป็นต้องใช้ความเข้าใจรายการ
Alexander

25

ประหลาดใจฉันยังไม่เห็นโพสต์นี้ดังนั้นฉันจะทิ้งไว้ที่นี่

ขยาย Iterable Unpacking (python3.5 +): [*df]และเพื่อน ๆ

การนำออกการแกะ (PEP 448)ได้รับการแนะนำด้วย Python 3.5 ดังนั้นการดำเนินการต่อไปนี้เป็นไปได้ทั้งหมด

df = pd.DataFrame('x', columns=['A', 'B', 'C'], index=range(5))
df

   A  B  C
0  x  x  x
1  x  x  x
2  x  x  x
3  x  x  x
4  x  x  x 

ถ้าคุณต้องการlist....

[*df]
# ['A', 'B', 'C']

หรือหากคุณต้องการset,

{*df}
# {'A', 'B', 'C'}

หรือหากคุณต้องการtuple,

*df,  # Please note the trailing comma
# ('A', 'B', 'C')

หรือถ้าคุณต้องการเก็บผลลัพธ์ไว้ที่ใดที่หนึ่ง

*cols, = df  # A wild comma appears, again
cols
# ['A', 'B', 'C']

... หากคุณเป็นคนที่แปลงกาแฟเป็นคนพิมพ์เสียงก็จะเป็นการบริโภคกาแฟของคุณอย่างมีประสิทธิภาพมากขึ้น;)

ป.ล. : ถ้าประสิทธิภาพเป็นสิ่งสำคัญคุณจะต้องทิ้งแนวทางแก้ไขปัญหาข้างต้นลงไป

df.columns.to_numpy().tolist()
# ['A', 'B', 'C']

นี้จะคล้ายกับคำตอบของเอ็ดชุมของแต่ปรับปรุงสำหรับ v0.24 ที่เป็นที่ต้องการการใช้งานของ.to_numpy() .valuesดู คำตอบนี้ (โดยฉัน) สำหรับข้อมูลเพิ่มเติม

การตรวจสอบด้วยสายตา
เนื่องจากฉันได้เห็นสิ่งนี้ถูกกล่าวถึงในคำตอบอื่นคุณสามารถใช้การเปิดกล่องที่ไม่ต้องทำซ้ำ (ไม่จำเป็นต้องใช้ลูปที่ชัดเจน)

print(*df)
A B C

print(*df, sep='\n')
A
B
C

คำติชมของวิธีการอื่น ๆ

อย่าใช้การforวนซ้ำอย่างชัดเจนสำหรับการดำเนินการที่สามารถทำได้ในบรรทัดเดียว (ความเข้าใจในรายการไม่เป็นไร)

ถัดไปการใช้sorted(df) จะไม่รักษาลำดับดั้งเดิมของคอลัมน์ไว้ เพื่อที่คุณควรใช้list(df)แทน

ถัดไปlist(df.columns)และlist(df.columns.values)เป็นข้อเสนอแนะที่ไม่ดี (ณ เวอร์ชันปัจจุบัน v0.24) ทั้งอาร์เรย์ (ส่งIndexคืนจากdf.columns) และ NumPy (คืนโดยdf.columns.values) กำหนด.tolist()วิธีการที่เร็วขึ้นและเป็นสำนวนมากขึ้น

สุดท้ายการรับฟังคือlist(df)ควรใช้เป็นทางเลือกที่กระชับกับวิธีการดังกล่าวข้างต้นสำหรับ python <= 3.4 โดยที่ไม่สามารถทำการขยายเพิ่มเติมได้


24

my_dataframe.columnsที่มีอยู่เป็น


1
และเป็นรายการอย่างชัดเจนโดยheader_list = list(my_dataframe.columns)
yeliabsalohcin

^ หรือยังดีกว่า: df.columns.tolist().
cs95

18

มันน่าสนใจ แต่df.columns.values.tolist()เร็วขึ้นเกือบ 3 เท่าแล้วdf.columns.tolist()แต่ฉันคิดว่ามันเหมือนกัน:

In [97]: %timeit df.columns.values.tolist()
100000 loops, best of 3: 2.97 µs per loop

In [98]: %timeit df.columns.tolist()
10000 loops, best of 3: 9.67 µs per loop

2
การกำหนดเวลาได้รับการกล่าวถึงในคำตอบนี้แล้ว เหตุผลของความคลาดเคลื่อนก็คือ.valuesส่งคืนอาเรย์ numpy ต้นแบบและการทำบางสิ่งที่มี numpy นั้นเกือบจะเร็วกว่าการทำสิ่งเดียวกันกับนุ่นโดยตรง
cs95

17

DataFrameตาม Dict เหมือนการประชุมของ iterating มากกว่า“กุญแจ” ของวัตถุ

my_dataframe.keys()

สร้างรายการของคีย์ / คอลัมน์ - วิธีการของวัตถุto_list()และวิธีการpythonic

my_dataframe.keys().to_list()
list(my_dataframe.keys())

การทำซ้ำขั้นพื้นฐานใน DataFrame ส่งคืนป้ายชื่อคอลัมน์

[column for column in my_dataframe]

อย่าแปลง DataFrame เป็นรายการเพียงเพื่อรับเลเบลคอลัมน์ อย่าหยุดคิดขณะค้นหาตัวอย่างรหัสที่สะดวก

xlarge = pd.DataFrame(np.arange(100000000).reshape(10000,10000))
list(xlarge) #compute time and memory consumption depend on dataframe size - O(N)
list(xlarge.keys()) #constant time operation - O(1)

2
การทดสอบของฉันแสดงdf.columnsได้เร็วกว่าdf.keys()มาก ไม่แน่ใจว่าทำไมพวกเขามีทั้งฟังก์ชั่นและคุณสมบัติสำหรับสิ่งเดียวกัน (ดีมันไม่ใช่ครั้งแรกที่ฉันได้เห็น 10 วิธีที่แตกต่างในการทำบางสิ่งในแพนด้า)
cs95

1
ความตั้งใจของคำตอบของฉันคือการแสดงสองสามวิธีในการสืบค้นป้ายชื่อคอลัมน์จาก DataFrame และไฮไลต์รูปแบบการต่อต้านประสิทธิภาพ อย่างไรก็ตามฉันชอบความคิดเห็นของคุณและยกระดับคำตอบล่าสุดของคุณ - เนื่องจากพวกเขาให้คุณค่าจากมุมมองด้านวิศวกรรมซอฟต์แวร์
Sascha Gottfried

14

ในโน้ตบุ๊ก

สำหรับการสำรวจข้อมูลในโน้ตบุ๊ก IPython วิธีที่ฉันชอบคือ:

sorted(df)

ซึ่งจะสร้างรายการเรียงตามลำดับตัวอักษรที่อ่านง่าย

ในที่เก็บรหัส

ในรหัสฉันคิดว่ามันชัดเจนมากขึ้นที่จะทำ

df.columns

เพราะมันบอกให้คนอื่นอ่านโค้ดของคุณว่าคุณกำลังทำอะไรอยู่


sorted(df)เปลี่ยนลำดับ ใช้ด้วยความระมัดระวัง
cs95

@coldspeed ฉันพูดถึงเรื่องนี้ว่า "ซึ่งจะสร้างรายการเรียงลำดับตามตัวอักษรที่อ่านง่าย"
fAllnx

9
%%timeit
final_df.columns.values.tolist()
948 ns ± 19.2 ns per loop (mean ± std. dev. of 7 runs, 1000000 loops each)
%%timeit
list(final_df.columns)
14.2 µs ± 79.1 ns per loop (mean ± std. dev. of 7 runs, 100000 loops each)
%%timeit
list(final_df.columns.values)
1.88 µs ± 11.7 ns per loop (mean ± std. dev. of 7 runs, 1000000 loops each)
%%timeit
final_df.columns.tolist()
12.3 µs ± 27.4 ns per loop (mean ± std. dev. of 7 runs, 100000 loops each)
%%timeit
list(final_df.head(1).columns)
163 µs ± 20.6 µs per loop (mean ± std. dev. of 7 runs, 10000 loops each)

3

ตอบโดย Simeon Visser ... คุณทำได้

list(my_dataframe.columns.values) 

หรือ

list(my_dataframe) # for less typing.

แต่ฉันคิดว่าจุดที่หวานที่สุดคือ:

list(my_dataframe.columns)

มันชัดเจนในเวลาเดียวกันไม่นานเกินความจำเป็น


"มันชัดเจนในเวลาเดียวกันไม่นานเกินความจำเป็น" ฉันไม่เห็นด้วย. การโทรlistไม่มีประโยชน์เว้นแต่คุณจะโทรdfโดยตรง (ตัวอย่างเช่นความกระชับ) การเข้าถึงแอ.columnsททริบิวต์จะส่งคืนIndexออบเจกต์ที่มีtolist()วิธีการกำหนดไว้และการโทรนั้นจะมีสำนวนมากกว่าการIndexฟัง การผสมสำนวนเพียงเพื่อความสมบูรณ์ไม่ใช่ความคิดที่ดี กันไปสำหรับ listifying .valuesอาร์เรย์ที่คุณได้รับจาก
cs95


3

สิ่งนี้ทำให้เรามีชื่อของคอลัมน์ในรายการ:

list(my_dataframe.columns)

ฟังก์ชั่นอื่นที่เรียกว่า tolist () สามารถใช้ได้เช่นกัน:

my_dataframe.columns.tolist()

สิ่งนี้ได้ถูกกล่าวถึงในคำตอบอื่น ๆ แล้ว ทางออกแรกของคุณผสมสำนวนซึ่งไม่ใช่ความคิดที่ดี ดูความคิดเห็นของฉันภายใต้คำตอบอื่น
cs95

2

ฉันรู้สึกว่าคำถามสมควรได้รับคำอธิบายเพิ่มเติม

ตามที่ @fixxxer บันทึกไว้คำตอบนั้นขึ้นอยู่กับเวอร์ชันของแพนด้าที่คุณใช้ในโครงการของคุณ ซึ่งคุณจะได้pd.__version__รับคำสั่งด้วย

หากคุณมีเหตุผลบางอย่างเช่นฉัน (ในเดเบียนเจสซีฉันใช้ 0.14.1) โดยใช้แพนด้ารุ่นเก่ากว่า 0.16.0 คุณต้องใช้:

df.keys().tolist()เพราะยังไม่มีdf.columnsวิธีการใช้งาน

ข้อดีของวิธีการของปุ่มนี้คือมันทำงานได้แม้ในแพนด้ารุ่นใหม่กว่าดังนั้นมันจึงเป็นสากลมากขึ้น


con of keys () คือการเรียกใช้ฟังก์ชันแทนที่จะเป็นการค้นหาแอททริบิวต์ดังนั้นมันจะช้าลงเสมอ แน่นอนว่าด้วยการเข้าถึงเวลาคงที่ไม่มีใครสนใจความแตกต่างเช่นนี้จริงๆ แต่ฉันคิดว่ามันควรค่าแก่การพูดถึงอยู่ดี df.columns เป็นสำนวนที่เป็นที่ยอมรับในระดับสากลมากขึ้นสำหรับการเข้าถึงส่วนหัว
cs95

1
n = []
for i in my_dataframe.columns:
    n.append(i)
print n

6
โปรดแทนที่ด้วยความเข้าใจในรายการ
Sascha Gottfried

4
เปลี่ยน 3 บรรทัดแรกของคุณเป็น[n for n in dataframe.columns]
Anton Protopopov

ทำไมคุณต้องการที่จะผ่านปัญหาทั้งหมดนี้สำหรับการดำเนินการที่คุณสามารถทำได้ง่ายๆในบรรทัดเดียว?
cs95

0

แม้ว่าวิธีแก้ปัญหาที่ให้ไว้ข้างต้นนั้นดี ฉันยังคาดหวังบางอย่างเช่น frame.column_names () ให้เป็นฟังก์ชันในนุ่น แต่เนื่องจากมันไม่ใช่อาจจะเป็นการดีถ้าใช้ไวยากรณ์ต่อไปนี้ อย่างใดมันจะรักษาความรู้สึกที่คุณใช้แพนด้าในวิธีที่เหมาะสมโดยการเรียกฟังก์ชั่น "tolist": frame.columns.tolist ()

frame.columns.tolist() 

0

หาก DataFrame มีดัชนีหรือ MultiIndex และคุณต้องการรวมไว้เป็นชื่อคอลัมน์ด้วย:

names = list(filter(None, df.index.names + df.columns.values.tolist()))

มันหลีกเลี่ยงการเรียกใช้ reset_index () ซึ่งมีประสิทธิภาพที่ไม่จำเป็นสำหรับการดำเนินการอย่างง่าย

ฉันจำเป็นต้องใช้สิ่งนี้บ่อยขึ้นเพราะฉันปิดการทำงานข้อมูลจากฐานข้อมูลที่ดัชนีของ dataframe แมปไปยังคีย์หลัก / ที่ไม่ซ้ำกัน แต่จริงๆแล้วเป็น "คอลัมน์" อีกอันสำหรับฉัน มันอาจจะเป็นเรื่องที่สมเหตุสมผลสำหรับแพนด้าที่มีวิธีการในตัวสำหรับบางสิ่งเช่นนี้


โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.