# Python 读写 CSV 文件

> 原文： [https://howtodoinjava.com/python/python-read-write-csv-files/](https://howtodoinjava.com/python/python-read-write-csv-files/)

学习在 [Python](https://www.python.org/) 中使用 **CSV** 文件。 CSV（逗号分隔值）格式是在电子表格和数据库中使用的非常流行的导入和导出格式。 Python 语言包含`csv`模块，该模块具有**可以读写 CSV 格式**的类。

```java
Table of Contents

Reading CSV file with csv.reader()
Reading CSV file with csv.DictReader
Writing CSV file using csv.writer()
Quoting
CSV Dialects
Custom CSV Dialects
```

## 使用`csv.reader()`读取 CSV 文件

[`csv.reader()`](https://docs.python.org/3/library/csv.html#csv.reader)方法返回一个读取器对象，该对象将遍历给定 CSV 文件中的行。

假设我们有以下包含数字的`numbers.csv`文件：

```java
6,5,3,9,8,6,7

```

以下 python 脚本从此 CSV 文件读取数据。

```java
#!/usr/bin/python3

import csv

f = open('numbers.csv', 'r')

with f:

    reader = csv.reader(f)
    for row in reader:
        print(row)

```

在上面的代码示例中，我们打开了`numbers.csv`进行读取，并使用`csv.reader()`方法加载了数据。

现在，假设 CSV 文件将使用**不同的定界符**。 （严格来说，这不是 CSV 文件，但是这种做法很常见。）例如，我们有以下`items.csv`文件，其中的元素由竖线字符（`|`）分隔：

```java
pen|table|keyboard

```

以下脚本从`items.csv`文件读取数据。

```java
#!/usr/bin/python3

import csv

f = open('items.csv', 'r')

with f:

    reader = csv.reader(f, delimiter="|")
    for row in reader:
        for e in row:
            print(e)

```

我们在`csv.reader()`方法中使用`delimiter`参数指定新的分隔字符。

## 使用`csv.DictReader`读取 CSV 文件

[`csv.DictReader`](https://docs.python.org/3/library/csv.html#csv.DictReader)类的操作类似于常规阅读器，但是将读取的信息映射到字典中。

字典的键可以使用`fieldnames`参数传入，也可以从 CSV 文件的第一行推断出来。

我们具有以下`values.csv`文件：

```java
min, avg, max
1, 5.5, 10

```

第一行代表字典的键，第二行代表值。

```java
#!/usr/bin/python3

import csv

f = open('values.csv', 'r')

with f:

    reader = csv.DictReader(f)
    for row in reader:
        print(row)

```

上面的 python 脚本使用`csv.DictReader`从`values.csv`文件读取值。

这是示例的输出。

```java
$ ./read_csv3.py 
{' max': ' 10', 'min': '1', ' avg': ' 5.5'}

```

## 使用`csv.writer()`写入 CSV 文件

[`csv.writer()`](https://docs.python.org/3/library/csv.html#csv.writer)方法返回一个写入器对象，该对象负责将用户数据转换为给定文件状对象上的定界字符串。

```java
#!/usr/bin/python3

import csv

nms = [[1, 2, 3, 4, 5, 6], [7, 8, 9, 10, 11, 12]]

f = open('numbers2.csv', 'w')

with f:

    writer = csv.writer(f)
    for row in nms:
        writer.writerow(row)

```

该脚本将数字写入`numbers2.csv`文件。 `writerow()`方法将一行数据写入指定的文件。

该脚本生成以下文件（`numbers2.csv`）：

```java
1,2,3,4,5,6
7,8,9,10,11,12

```

一次写入所有数据是可能的。 `writerows()`方法将所有给定的行写入 CSV 文件。

下一个代码示例将 Python 列表写入`numbers3.csv`文件。 该脚本将三行数字写入文件。

```java
#!/usr/bin/python3

import csv

nms = [[1, 2, 3], [7, 8, 9], [10, 11, 12]]

f = open('numbers3.csv', 'w')

with f:

    writer = csv.writer(f)
    writer.writerows(nms)

```

运行上述程序时，以下输出将写入`numbers3.csv`文件：

```java
1,2,3
7,8,9
10,11,12

```

## 报价单

可以在 CSV 文件中引用单词。 Python CSV 模块中有**四种不同的引用模式**：

*   `QUOTE_ALL` — 引用所有字段
*   `QUOTE_MINIMAL` - 仅引用包含特殊字符的字段
*   `QUOTE_NONNUMERIC` — 引用所有非数字字段
*   `QUOTE_NONE` — 不引用字段

在下一个示例中，我们将三行写入`items2.csv`文件。 所有非数字字段均用引号引起来。

```java
#!/usr/bin/python3

import csv

f = open('items2.csv', 'w')

with f:

    writer = csv.writer(f, quoting=csv.QUOTE_NONNUMERIC)
    writer.writerows((["coins", 3], ["pens", 2], ["bottles", 7]))

```

该程序将创建以下`items2.csv`文件。 引用项目名称，不引用数字表示的数量。

```java
"coins",3
"pens",2
"bottles",7

```

## CSV 方言

尽管 CSV 格式是一种非常简单的格式，但还是有许多差异，例如不同的定界符，换行或引号字符。 因此，有不同的 CSV 方言可用。

下一个代码示例将打印可用的方言及其特征。

```java
#!/usr/bin/python3

import csv

names = csv.list_dialects()

for name in names:

    print(name)

    dialect = csv.get_dialect(name)

    print(repr(dialect.delimiter), end=" ")
    print(dialect.doublequote, end=" ")
    print(dialect.escapechar, end=" ")
    print(repr(dialect.lineterminator), end=" ")
    print(dialect.quotechar, end=" ")
    print(dialect.quoting, end=" ")
    print(dialect.skipinitialspace, end=" ")
    print(dialect.strict)

```

`csv.list_dialects()`返回方言名称的列表，`csv.get_dialect()`方法返回与方言名称关联的方言。

```java
$ ./dialects.py 
excel
',' 1 None '\r\n' " 0 0 0
excel-tab
'\t' 1 None '\r\n' " 0 0 0
unix
',' 1 None '\n' " 1 0 0

```

程序将打印此输出。 内置三种方言：`excel`，`excel-tab`和`unix`。

## 自定义 CSV 方言

在本教程的最后一个示例中，我们将创建一个自定义方言。 使用`csv.register_dialect()`方法创建自定义方言。

```java
#!/usr/bin/python3

import csv

csv.register_dialect("hashes", delimiter="#")

f = open('items3.csv', 'w')

with f:

    writer = csv.writer(f, dialect="hashes")
    writer.writerow(("pencils", 2)) 
    writer.writerow(("plates", 1))
    writer.writerow(("books", 4))

```

该程序使用（`#`）字符作为分隔符。 使用`csv.writer()`方法中的`dialect`选项指定方言。

程序生成以下文件（`items3.csv`）：

```java
pencils#2
plates#1
books#4

```

在本教程中，我们探索了 Python `csv`模块，并通过了一些**在 python** 中读写 CSV 文件的示例。

学习愉快！

该教程由运行 [zetcode.com](http://zetcode.com) 的 Jan Bodnar 编写。