J'utilise python sur Spark et je voudrais obtenir un csv dans un cadre de données.
La documentation pour Spark SQL ne fournit étrangement pas d'explications sur CSV en tant que source.
J'ai trouvé Spark-CSV , mais j'ai des problèmes avec deux parties de la documentation:
"This package can be added to Spark using the --jars command line option. For example, to include it when starting the spark Shell: $ bin/spark-Shell --packages com.databricks:spark-csv_2.10:1.0.3"
Ai-je vraiment besoin d'ajouter cet argument chaque fois que je lance pyspark ou spark-submit? Cela semble très inélégant. N'y a-t-il pas moyen de l'importer en python plutôt que de le retélécharger à chaque fois?
df = sqlContext.load(source="com.databricks.spark.csv", header="true", path = "cars.csv")
Même si je fais ce qui précède, cela ne fonctionnera pas. Qu'est-ce que l'argument "source" représente dans cette ligne de code? Comment charger simplement un fichier local sur Linux, par exemple "/Spark_Hadoop/spark-1.3.1-bin-cdh4/cars.csv"?
Lisez le fichier csv dans un RDD, puis générez un RowRDD à partir du RDD d’origine.
Créez le schéma représenté par un StructType correspondant à la structure des lignes du RDD créé à l'étape 1.
Appliquez le schéma au RDD de lignes via la méthode createDataFrame fournie par SQLContext.
lines = sc.textFile("examples/src/main/resources/people.txt")
parts = lines.map(lambda l: l.split(","))
# Each line is converted to a Tuple.
people = parts.map(lambda p: (p[0], p[1].strip()))
# The schema is encoded in a string.
schemaString = "name age"
fields = [StructField(field_name, StringType(), True) for field_name in schemaString.split()]
schema = StructType(fields)
# Apply the schema to the RDD.
schemaPeople = spark.createDataFrame(people, schema)
source: GUIDE DE PROGRAMMATION SPARK
from pyspark.sql.types import StringType
from pyspark import SQLContext
sqlContext = SQLContext(sc)
Employee_rdd = sc.textFile("\..\Employee.csv")
.map(lambda line: line.split(","))
Employee_df = Employee_rdd.toDF(['Employee_ID','Employee_name'])
Employee_df.show()
Avec les versions plus récentes de Spark (à partir de la version 1.4, je crois), cela est devenu beaucoup plus facile. L'expression sqlContext.read
vous donne une DataFrameReader
instance, avec une méthode .csv()
:
df = sqlContext.read.csv("/path/to/your.csv")
Notez que vous pouvez également indiquer que le fichier csv a un en-tête en ajoutant le mot clé argument header=True
à l'appel .csv()
. Une poignée d'autres options sont disponibles et décrites dans le lien ci-dessus.
Si la dépendance de paquet supplémentaire ne vous dérange pas, vous pouvez utiliser des pandas pour analyser le fichier CSV. Il gère très bien les virgules internes.
Les dépendances:
from pyspark import SparkContext
from pyspark.sql import SQLContext
import pandas as pd
Lisez tout le fichier en une fois dans un fichier de données Spark:
sc = SparkContext('local','example') # if using locally
sql_sc = SQLContext(sc)
pandas_df = pd.read_csv('file.csv') # assuming the file contains a header
# If no header:
# pandas_df = pd.read_csv('file.csv', names = ['column 1','column 2'])
s_df = sql_sc.createDataFrame(pandas_df)
Ou, encore plus conscient des données, vous pouvez fractionner les données dans un Spark RDD puis DF:
chunk_100k = pd.read_csv('file.csv', chunksize=100000)
for chunky in chunk_100k:
Spark_temp_rdd = sc.parallelize(chunky.values.tolist())
try:
Spark_full_rdd += Spark_temp_rdd
except NameError:
Spark_full_rdd = Spark_temp_rdd
del Spark_temp_rdd
Spark_DF = Spark_full_rdd.toDF(['column 1','column 2'])
Après Spark 2.0, il est recommandé d’utiliser une session Spark:
from pyspark.sql import SparkSession
from pyspark.sql import Row
# Create a SparkSession
spark = SparkSession \
.builder \
.appName("basic example") \
.config("spark.some.config.option", "some-value") \
.getOrCreate()
def mapper(line):
fields = line.split(',')
return Row(ID=int(fields[0]), field1=str(fields[1].encode("utf-8")), field2=int(fields[2]), field3=int(fields[3]))
lines = spark.sparkContext.textFile("file.csv")
df = lines.map(mapper)
# Infer the schema, and register the DataFrame as a table.
schemaDf = spark.createDataFrame(df).cache()
schemaDf.createOrReplaceTempView("tablename")
pour Pyspark, en supposant que la première ligne du fichier csv contient un en-tête
spark = SparkSession.builder.appName('chosenName').getOrCreate()
df=spark.read.csv('fileNameWithPath', mode="DROPMALFORMED",inferSchema=True, header = True)
J'ai rencontré un problème similaire. La solution consiste à ajouter une variable d'environnement nommée "PYSPARK_SUBMIT_ARGS" et à définir sa valeur sur "--packages com.databricks: spark-csv_2.10: 1.4.0 pyspark-Shell". Cela fonctionne avec le shell interactif Python de Spark.
Assurez-vous de faire correspondre la version de spark-csv avec la version de Scala installée. Avec Scala 2.11, il s’agit de spark-csv_2.11 et avec Scala 2.10 ou 2.10.5, il s’agit de spark-csv_2.10.
Esperons que ça marche.
Basé sur la réponse de Aravind, mais beaucoup plus court, par exemple. :
lines = sc.textFile("/path/to/file").map(lambda x: x.split(","))
df = lines.toDF(["year", "month", "day", "count"])