PySpark Õpetus algajatele: õppige NÄIDETE abil
Enne PySpark, mõistame:
Mis on Apache Spark?
Spark on suurandmete lahendus, mis on osutunud lihtsamaks ja kiiremaks kui Hadoop MapReduce. Spark on avatud lähtekoodiga tarkvara, mille töötas välja UC Berkeley RAD lab 2009. aastal. Alates selle avalikkusele avaldamisest 2010. aastal, Spark populaarsus on kasvanud ja seda kasutatakse tööstuses enneolematul määral.
Ajastul Big andmed, vajavad praktikud andmete voogesituse töötlemiseks kiireid ja usaldusväärseid tööriistu rohkem kui kunagi varem. Varasemad tööriistad, nagu MapReduce, olid lemmikud, kuid olid aeglased. Selle probleemi lahendamiseks Spark pakub nii kiiret kui ka üldotstarbelist lahendust. Peamine erinevus Spark ja MapReduce on see Spark töötab kõvakettal hilisemal ajal arvutusi mälus. See võimaldab kiiret juurdepääsu ja andmete töötlemist, vähendades aega tundidest minutiteni.
Mis on PySpark?
PySpark on Apache loodud tööriist Spark Kogukond kasutamiseks Python koos Spark. See võimaldab töötada RDD-ga (resilient Distributed Dataset). Python. Samuti pakub see PySpark Shell linkimiseks Python API-d koos Spark tuum algatada Spark Sisu. Spark on klastri andmetöötluse realiseerimiseks mõeldud mootor, samas kui PySpark is Pythonkasutada raamatukogu Spark.
Kuidas Spark tööd?
Spark põhineb arvutusmootoril, mis tähendab, et see hoolitseb rakenduste ajastamise, levitamise ja jälgimise eest. Iga ülesannet tehakse erinevates töömasinates, mida nimetatakse arvutusklastriteks. Arvutusklaster viitab ülesannete jaotusele. Üks masin täidab ühte ülesannet, teised panustavad lõppväljundisse läbi erineva ülesande. Lõpuks koondatakse kõik ülesanded väljundi saamiseks. The Spark admin annab 360-kraadise ülevaate erinevatest Spark Töökohad.

Spark on mõeldud töötamiseks
- Python
- Java
- Scala
- SQL
Märkimisväärne omadus Spark on suur hulk sisseehitatud teeki, sealhulgas masinõppe jaoks mõeldud MLlib. Spark on loodud töötama ka Hadoopi klastritega ja suudab lugeda laia tüüpi faile, sealhulgas Hive'i andmeid, CSV-d, JSON-i ja Casandra andmeid.
Miks kasutada Spark?
Tulevase andmepraktikuna peaksite olema tuttav Pythoni kuulsate raamatukogudega: Pandas ja scikit-learn. Need kaks teeki sobivad suurepäraselt keskmise suurusega andmestiku uurimiseks. Regulaarsed masinõppeprojektid on üles ehitatud järgmise metoodika ümber.
- Laadige andmed kettale
- Importige andmed masina mällu
- Töötle/analüüsi andmeid
- Looge masinõppe mudel
- Salvestage ennustus tagasi kettale
Probleem tekib siis, kui andmeteadlane soovib töödelda andmeid, mis on ühe arvuti jaoks liiga suured. Andmeteaduse varasematel päevadel võtsid praktikud proovidest, kuna tohutute andmekogumite koolitust polnud alati vaja. Andmeteadlane leiaks hea statistilise valimi, viiks läbi täiendava töökindluse kontrolli ja leiaks suurepärase mudeli.
Sellega on siiski mõned probleemid:
- Kas andmestik peegeldab tegelikku maailma?
- Kas andmed sisaldavad konkreetset näidet?
- Kas mudel sobib proovivõtuks?
Võtke näiteks kasutajate soovitused. Soovitajad toetuvad nende eelistuste hindamisel kasutajate võrdlemisele teiste kasutajatega. Kui andmekasutaja võtab ainult andmete alamhulga, ei ole kasutajate rühma, kes on üksteisega väga sarnased. Soovitajad peavad töötama kogu andmestikuga või üldse mitte.
Mis on lahendus?
Lahendus on olnud ilmne juba pikka aega, jagage probleem mitmele arvutile. Paralleelarvutiga kaasneb ka mitmeid probleeme. Arendajatel on sageli probleeme paralleelkoodi kirjutamisega ja nad peavad lahendama hulga keerulisi probleeme, mis on seotud mitme töötlemise endaga.
Pyspark annab andmeteadlasele API, mida saab kasutada paralleelsete andmete töötlemise probleemide lahendamiseks. Pyspark tegeleb mitmetöötluse keerukusega, nagu andmete jaotamine, koodi jagamine ja masinate klastri töötajatelt väljundi kogumine.
Spark saab töötada eraldiseisvana, kuid enamasti töötab see klastri arvutusraamistiku peal, näiteks Hadoop. Testimisel ja arendusel saab andmeteadlane aga tõhusalt töötada Spark arenduskastides või ilma klastrita sülearvutites
• Üks peamisi eeliseid Spark eesmärk on luua arhitektuur, mis hõlmab andmete voogesituse haldust, sujuvaid andmepäringuid, masinõppe ennustamist ja reaalajas juurdepääsu erinevatele analüüsidele.
• Spark töötab tihedalt SQL-keelega, st struktureeritud andmetega. See võimaldab reaalajas andmeid pärida.
• Andmeteadlase põhitöö on ennustavate mudelite analüüsimine ja koostamine. Lühidalt, andmeteadlane peab teadma, kuidas andmeid kasutades päringuid teha SQL, koostada statistilist aruannet ja kasutada prognooside koostamiseks masinõpet. Andmeteadlane kulutab märkimisväärse osa oma ajast andmete puhastamisele, muutmisele ja analüüsimisele. Kui andmekogum või andmete töövoog on valmis, kasutab andmeteadlane teadmisi ja peidetud mustreid avastamaks erinevaid tehnikaid. Andmetöötlus peaks olema tugev ja sama lihtne kasutada. Spark on õige tööriist tänu oma kiirusele ja rikkalikele API-dele.
Selles PySpark õpetusest saate teada, kuidas Py abil klassifikaatorit koostadaSpark näited.
Kuidas installida PySpark koos AWS-iga
. Jupyter meeskond loob käitamiseks Dockeri pildi Spark tõhusalt. Allpool on toodud juhised, mida saate Py installimiseks järgidaSpark näiteks AWS-is.
Vaadake meie õpetust AWS ja TensorFlow
1. toiming: looge eksemplar
Kõigepealt peate looma eksemplari. Minge oma AWS-i kontole ja käivitage eksemplar. Saate suurendada salvestusruumi kuni 15 g-ni ja kasutada sama turvarühma nagu TensorFlow õpetuses.
2. samm: avage ühendus
Avage ühendus ja paigaldage dokkimiskonteiner. Lisateavet leiate TensorFlow koos õpetusest laevalaadija. Pange tähele, et peate olema õiges töökataloogis.
Dockeri installimiseks käivitage lihtsalt need koodid:
sudo yum update -y sudo yum install -y docker sudo service docker start sudo user-mod -a -G docker ec2-user exit
3. samm: avage ühendus uuesti ja installige Spark
Pärast ühenduse taasavamist saate installida Py-d sisaldava pildiSpark.
## Spark docker run -v ~/work:/home/jovyan/work -d -p 8888:8888 jupyter/pyspark-notebook ## Allow preserving Jupyter notebook sudo chown 1000 ~/work ## Install tree to see our working directory next sudo yum install -y tree
Samm 4: avatud Jupyter
Kontrollige konteinerit ja selle nime
docker ps
Käivitage dokk koos dokkimislogidega, millele järgneb dokkija nimi. Näiteks docker logib zealous_goldwasser
Minge oma brauserisse ja käivitage Jupyter. Aadress on http://localhost:8888/. Kleepige terminali antud parool.
märkused: kui soovite faili oma AWS-seadmesse üles laadida/alla laadida, võite kasutada tarkvara Cyberduck, https://cyberduck.io/.
Kuidas installida PySpark on Windows/Mac koos Condaga
Järgmine on Py installimise üksikasjalik protsessSpark on Windows/Mac, mis kasutab Anacondat:
Paigaldada Spark oma kohalikus masinas on soovitatav luua uus conda keskkond. See uus keskkond installitakse Python 3.6 Spark ja kõik sõltuvused.
Maci kasutaja
cd anaconda3 touch hello-spark.yml vi hello-spark.yml
Windows Kasutaja
cd C:\Users\Admin\Anaconda3 echo.>hello-spark.yml notepad hello-spark.yml
Saate redigeerida .yml-faili. Olge taandega ettevaatlik. Enne on vaja kahte tühikut -
name: hello-spark
dependencies:
- python=3.6
- jupyter
- ipython
- numpy
- numpy-base
- pandas
- py4j
- pyspark
- pytz
Salvestage see ja looge keskkond. See võtab natuke aega
conda env create -f hello-spark.yml
Asukoha kohta lisateabe saamiseks vaadake TensorFlow installimise õpetust
Saate kontrollida kogu teie masinasse installitud keskkonda
conda env list
Activate hello-spark
Maci kasutaja
source activate hello-spark
Windows Kasutaja
activate hello-spark
Märge: Olete juba loonud konkreetse TensorFlow keskkonna, et TensorFlow's õpetusi käitada. Mugavam on luua uus, hello-tf-st erinev keskkond. Pole mõtet hello-tf-iga üle koormata Spark või mis tahes muud masinõppe teegid.
Kujutage ette, et suurem osa teie projektist hõlmab TensorFlow, kuid peate seda kasutama Spark ühe konkreetse projekti jaoks. Saate määrata kogu oma projekti jaoks TensorFlow keskkonna ja luua selle jaoks eraldi keskkonna Spark. Saate lisada nii palju teeke Spark keskkonda, nagu soovite, ilma TensorFlow keskkonda segamata. Kui olete lõpetanud Sparkprojekti, saate selle kustutada ilma TensorFlow keskkonda mõjutamata.
Jupyter
avatud Jupyter Märkmik ja proovige, kas PySpark töötab. Kleepige uude märkmikku järgmine PySpark näidiskood:
import pyspark from pyspark import SparkContext sc =SparkContext()
Kui kuvatakse viga, on see tõenäoline Java pole teie masinasse installitud. Macis ava terminal ja kirjuta java -version, kui on java versioon, siis vaata et see oleks 1.8. sisse Windows, avage rakendus ja kontrollige, kas seal on a Java kausta. Kui on olemas a Java kaust, kontrolli seda Java 1.8 on paigaldatud. Selle kirjutamise seisuga on PySpark ei ühildu Java9 ja üle selle.
Kui teil on vaja installida Java, sa mõtled link ja laadige alla jdk-8u181-windows-x64.exe
Maci kasutajate jaoks on soovitatav kasutada `brew.`
brew tap caskroom/versions brew cask install java8
Vaadake seda samm-sammult õpetust kuidas paigaldada Java
märkused: Kasutage keskkonna täielikuks kustutamiseks nuppu Remove.
conda env remove -n hello-spark -y
Spark kontekst
SparkKontekst on sisemine mootor, mis võimaldab ühendusi klastritega. Kui soovite operatsiooni läbi viia, peate a SparkSisu.
Loo Sparkkontekst
Kõigepealt peate algatama a SparkSisu.
import pyspark from pyspark import SparkContext sc =SparkContext()
Nüüd, kui SparkKontekst on valmis, saate luua andmete kogumi nimega RDD, Resilient Distributed Dataset. Arvutamine RDD-s paralleelseeritakse automaatselt kogu klastri ulatuses.
nums= sc.parallelize([1,2,3,4])
Esimesele reale pääsete juurde võtmisega
nums.take(1)
[1]
Andmetele saab teisenduse rakendada lambda-funktsiooniga. Rakenduses PySpark allolevas näites tagastate numbrite ruudu. See on kaardi teisendus
squared = nums.map(lambda x: x*x).collect()
for num in squared:
print('%i ' % (num))
1 4 9 16
SQLContext
Mugavam viis on kasutada DataFrame'i. SparkKontekst on juba määratud, saate seda kasutada dataFrame'i loomiseks. Samuti peate deklareerima SQLContexti
SQLContext võimaldab mootorit ühendada erinevate andmeallikatega. Seda kasutatakse funktsioonide käivitamiseks Spark sql.
from pyspark.sql import Row from pyspark.sql import SQLContext sqlContext = SQLContext(sc)
Nüüd selles Spark juhendaja Python, loome korteeži loendi. Iga korteež sisaldab inimeste nime ja vanust. Nõutavad on neli sammu:
Step 1) Looge teabega korteeži loend
[('John',19),('Smith',29),('Adam',35),('Henry',50)]
Step 2) Ehitage RDD
rdd = sc.parallelize(list_p)
Step 3) Teisenda korteid
rdd.map(lambda x: Row(name=x[0], age=int(x[1])))
Step 4) Looge DataFrame'i kontekst
sqlContext.createDataFrame(ppl)
list_p = [('John',19),('Smith',29),('Adam',35),('Henry',50)]
rdd = sc.parallelize(list_p)
ppl = rdd.map(lambda x: Row(name=x[0], age=int(x[1])))
DF_ppl = sqlContext.createDataFrame(ppl)
Kui soovite juurde pääseda iga funktsiooni tüübile, saate kasutada printSchema()
DF_ppl.printSchema() root |-- age: long (nullable = true) |-- name: string (nullable = true)
Masinõppe näide Py-gaSpark
Nüüd, kui teil on lühike idee Spark ja SQLContext, olete valmis looma oma esimese masinõppeprogrammi.
Järgmised sammud Py-ga masinõppeprogrammi loomiseksSpark:
- Step 1) Põhioperatsioon Py-gaSpark
- Step 2) Andmete eeltöötlemine
- Step 3) Ehitage andmetöötluse torujuhe
- Step 4) Ehitage klassifikaator: logistika
- Step 5) Treenige ja hinnake mudelit
- Step 6) Häälestage hüperparameeter
Selles PySpark Masinõppe õpetus, kasutame täiskasvanutele mõeldud andmestikku. Selle õpetuse eesmärk on õppida Pysparki kasutama. Andmestiku kohta lisateabe saamiseks vaadake seda õpetust.
Pange tähele, et andmestik ei ole oluline ja võite arvata, et arvutamine võtab kaua aega. Spark on mõeldud suure hulga andmete töötlemiseks. SparkKui töödeldav andmekogum suureneb, suureneb selle jõudlus võrreldes teiste masinõppeteekidega.
Samm 1) Põhioperatsioon Py-gaSpark
Esiteks peate lähtestama SQLContexti, mis pole veel algatatud.
#from pyspark.sql import SQLContext url = "https://raw.githubusercontent.com/guru99-edu/R-Programming/master/adult_data.csv" from pyspark import SparkFiles sc.addFile(url) sqlContext = SQLContext(sc)
Seejärel saate cvs-faili lugeda failiga sqlContext.read.csv. Teatamiseks kasutate inferSchema väärtuseks Tõene Spark andmete tüübi automaatseks äraarvamiseks. Vaikimisi on see väärtuseks False.
df = sqlContext.read.csv(SparkFiles.get("adult_data.csv"), header=True, inferSchema= True)
Vaatame andmetüüpi
df.printSchema() root |-- age: integer (nullable = true) |-- workclass: string (nullable = true) |-- fnlwgt: integer (nullable = true) |-- education: string (nullable = true) |-- education_num: integer (nullable = true) |-- marital: string (nullable = true) |-- occupation: string (nullable = true) |-- relationship: string (nullable = true) |-- race: string (nullable = true) |-- sex: string (nullable = true) |-- capital_gain: integer (nullable = true) |-- capital_loss: integer (nullable = true) |-- hours_week: integer (nullable = true) |-- native_country: string (nullable = true) |-- label: string (nullable = true)
Andmeid näete show abil.
df.show(5, truncate = False)
+---+----------------+------+---------+-------------+------------------+-----------------+-------------+-----+------+------------+------------+----------+--------------+-----+ |age|workclass |fnlwgt|education|education_num|marital |occupation |relationship |race |sex |capital_gain|capital_loss|hours_week|native_country|label| +---+----------------+------+---------+-------------+------------------+-----------------+-------------+-----+------+------------+------------+----------+--------------+-----+ |39 |State-gov |77516 |Bachelors|13 |Never-married |Adm-clerical |Not-in-family|White|Male |2174 |0 |40 |United-States |<=50K| |50 |Self-emp-not-inc|83311 |Bachelors|13 |Married-civ-spouse|Exec-managerial |Husband |White|Male |0 |0 |13 |United-States |<=50K| |38 |Private |215646|HS-grad |9 |Divorced |Handlers-cleaners|Not-in-family|White|Male |0 |0 |40 |United-States |<=50K| |53 |Private |234721|11th |7 |Married-civ-spouse|Handlers-cleaners|Husband |Black|Male |0 |0 |40 |United-States |<=50K| |28 |Private |338409|Bachelors|13 |Married-civ-spouse|Prof-specialty |Wife |Black|Female|0 |0 |40 |Cuba |<=50K| +---+----------------+------+---------+-------------+------------------+-----------------+-------------+-----+------+------------+------------+----------+--------------+-----+ only showing top 5 rows
Kui te ei määranud inderShema väärtuseks Tõene, toimub tüübiga järgmine. Seal on kõik stringis.
df_string = sqlContext.read.csv(SparkFiles.get("adult.csv"), header=True, inferSchema= False)
df_string.printSchema()
root
|-- age: string (nullable = true)
|-- workclass: string (nullable = true)
|-- fnlwgt: string (nullable = true)
|-- education: string (nullable = true)
|-- education_num: string (nullable = true)
|-- marital: string (nullable = true)
|-- occupation: string (nullable = true)
|-- relationship: string (nullable = true)
|-- race: string (nullable = true)
|-- sex: string (nullable = true)
|-- capital_gain: string (nullable = true)
|-- capital_loss: string (nullable = true)
|-- hours_week: string (nullable = true)
|-- native_country: string (nullable = true)
|-- label: string (nullable = true)
Pideva muutuja õigesse vormingusse teisendamiseks võite kasutada veergude ümbersõnastamist. Saate kasutada koos Column abil Spark millises veerus teisendust kasutada.
# Import all from `sql.types`
from pyspark.sql.types import *
# Write a custom function to convert the data type of DataFrame columns
def convertColumn(df, names, newType):
for name in names:
df = df.withColumn(name, df[name].cast(newType))
return df
# List of continuous features
CONTI_FEATURES = ['age', 'fnlwgt','capital_gain', 'education_num', 'capital_loss', 'hours_week']
# Convert the type
df_string = convertColumn(df_string, CONTI_FEATURES, FloatType())
# Check the dataset
df_string.printSchema()
root
|-- age: float (nullable = true)
|-- workclass: string (nullable = true)
|-- fnlwgt: float (nullable = true)
|-- education: string (nullable = true)
|-- education_num: float (nullable = true)
|-- marital: string (nullable = true)
|-- occupation: string (nullable = true)
|-- relationship: string (nullable = true)
|-- race: string (nullable = true)
|-- sex: string (nullable = true)
|-- capital_gain: float (nullable = true)
|-- capital_loss: float (nullable = true)
|-- hours_week: float (nullable = true)
|-- native_country: string (nullable = true)
|-- label: string (nullable = true)
from pyspark.ml.feature import StringIndexer
#stringIndexer = StringIndexer(inputCol="label", outputCol="newlabel")
#model = stringIndexer.fit(df)
#df = model.transform(df)
df.printSchema()
Valige veerud
Saate valida ja kuvada ridu valiku ja funktsioonide nimedega. Allpool on valitud vanus ja fnlwgt.
df.select('age','fnlwgt').show(5)
+---+------+ |age|fnlwgt| +---+------+ | 39| 77516| | 50| 83311| | 38|215646| | 53|234721| | 28|338409| +---+------+ only showing top 5 rows
Loenda rühmade kaupa
Kui soovite loendada esinemiste arvu rühmade kaupa, saate aheldada:
- groupBy()
- count ()
koos. Rakenduses PySpark allolevas näites loete ridade arvu haridustaseme järgi.
df.groupBy("education").count().sort("count",ascending=True).show()
+------------+-----+ | education|count| +------------+-----+ | Preschool| 51| | 1st-4th| 168| | 5th-6th| 333| | Doctorate| 413| | 12th| 433| | 9th| 514| | Prof-school| 576| | 7th-8th| 646| | 10th| 933| | Assoc-acdm| 1067| | 11th| 1175| | Assoc-voc| 1382| | Masters| 1723| | Bachelors| 5355| |Some-college| 7291| | HS-grad|10501| +------------+-----+
Kirjeldage andmeid
Andmete kokkuvõtliku statistika saamiseks võite kasutada kirjeldavat(). See arvutab välja:
- loe
- keskmine
- standardhälve
- minutit
- max
df.describe().show()
+-------+------------------+-----------+------------------+------------+-----------------+--------+----------------+------------+------------------+------+------------------+----------------+------------------+--------------+-----+ |summary| age| workclass| fnlwgt| education| education_num| marital| occupation|relationship| race| sex| capital_gain| capital_loss| hours_week|native_country|label| +-------+------------------+-----------+------------------+------------+-----------------+--------+----------------+------------+------------------+------+------------------+----------------+------------------+--------------+-----+ | count| 32561| 32561| 32561| 32561| 32561| 32561| 32561| 32561| 32561| 32561| 32561| 32561| 32561| 32561|32561| | mean| 38.58164675532078| null|189778.36651208502| null| 10.0806793403151| null| null| null| null| null|1077.6488437087312| 87.303829734959|40.437455852092995| null| null| | stddev|13.640432553581356| null|105549.97769702227| null|2.572720332067397| null| null| null| null| null| 7385.292084840354|402.960218649002|12.347428681731838| null| null| | min| 17| ?| 12285| 10th| 1|Divorced| ?| Husband|Amer-Indian-Eskimo|Female| 0| 0| 1| ?|<=50K| | max| 90|Without-pay| 1484705|Some-college| 16| Widowed|Transport-moving| Wife| White| Male| 99999| 4356| 99| Yugoslavia| >50K| +-------+------------------+-----------+------------------+------------+-----------------+--------+----------------+------------+------------------+------+------------------+----------------+------------------+--------------+-----+
Kui soovite kokkuvõtvat statistikat ainult ühe veeru kohta, lisage veeru nimi sisse description()
df.describe('capital_gain').show()
+-------+------------------+ |summary| capital_gain| +-------+------------------+ | count| 32561| | mean|1077.6488437087312| | stddev| 7385.292084840354| | min| 0| | max| 99999| +-------+------------------+
Risttabeli arvutamine
Mõnel juhul võib olla huvitav vaadata kirjeldavat statistikat kahe paaripõhise veeru vahel. Näiteks saate haridustaseme järgi loendada inimeste arvu, kelle sissetulek on alla või üle 50 XNUMX. Seda toimingut nimetatakse risttabeliks.
df.crosstab('age', 'label').sort("age_label").show()
+---------+-----+----+ |age_label|<=50K|>50K| +---------+-----+----+ | 17| 395| 0| | 18| 550| 0| | 19| 710| 2| | 20| 753| 0| | 21| 717| 3| | 22| 752| 13| | 23| 865| 12| | 24| 767| 31| | 25| 788| 53| | 26| 722| 63| | 27| 754| 81| | 28| 748| 119| | 29| 679| 134| | 30| 690| 171| | 31| 705| 183| | 32| 639| 189| | 33| 684| 191| | 34| 643| 243| | 35| 659| 217| | 36| 635| 263| +---------+-----+----+ only showing top 20 rows
Näete, et ühelgi inimesel pole noorena tulu üle 50 XNUMX.
Langetage veerg
Veergude eemaldamiseks on kaks intuitiivset API-t:
- drop(): kukutage veerg
- dropna(): Drop NA's
Allpool kukutate veeru hariduse_num
df.drop('education_num').columns
['age',
'workclass',
'fnlwgt',
'education',
'marital',
'occupation',
'relationship',
'race',
'sex',
'capital_gain',
'capital_loss',
'hours_week',
'native_country',
'label']
Andmete filtreerimine
Saate kasutada filtrit () kirjeldava statistika rakendamiseks andmete alamhulgale. Näiteks saate lugeda üle 40-aastaste inimeste arvu
df.filter(df.age > 40).count()
13443
Descriptive statistika rühmade kaupa
Lõpuks saate andmeid rühmitada rühmade kaupa ja arvutada statistilisi toiminguid nagu keskmine.
df.groupby('marital').agg({'capital_gain': 'mean'}).show()
+--------------------+------------------+ | marital| avg(capital_gain)| +--------------------+------------------+ | Separated| 535.5687804878049| | Never-married|376.58831788823363| |Married-spouse-ab...| 653.9832535885167| | Divorced| 728.4148098131893| | Widowed| 571.0715005035247| | Married-AF-spouse| 432.6521739130435| | Married-civ-spouse|1764.8595085470085| +--------------------+------------------+
Etapp 2) Andmete eeltöötlus
Andmetöötlus on masinõppes kriitiline samm. Pärast prügiandmete eemaldamist saate olulist teavet.
Näiteks teate, et vanus ei ole sissetulekuga lineaarne funktsioon. Kui inimesed on noored, on nende sissetulek tavaliselt väiksem kui keskeas. Pärast pensionile jäämist kasutab leibkond oma sääste, mis tähendab sissetulekute vähenemist. Selle mustri jäädvustamiseks võite lisada vanusefunktsioonile ruudu
Lisage vanuse ruut
Uue funktsiooni lisamiseks peate tegema järgmist.
- Valige veerg
- Rakendage teisendus ja lisage see DataFrame'i
from pyspark.sql.functions import *
# 1 Select the column
age_square = df.select(col("age")**2)
# 2 Apply the transformation and add it to the DataFrame
df = df.withColumn("age_square", col("age")**2)
df.printSchema()
root
|-- age: integer (nullable = true)
|-- workclass: string (nullable = true)
|-- fnlwgt: integer (nullable = true)
|-- education: string (nullable = true)
|-- education_num: integer (nullable = true)
|-- marital: string (nullable = true)
|-- occupation: string (nullable = true)
|-- relationship: string (nullable = true)
|-- race: string (nullable = true)
|-- sex: string (nullable = true)
|-- capital_gain: integer (nullable = true)
|-- capital_loss: integer (nullable = true)
|-- hours_week: integer (nullable = true)
|-- native_country: string (nullable = true)
|-- label: string (nullable = true)
|-- age_square: double (nullable = true)
Näete, et vanuse_ruut on edukalt andmeraami lisatud. Muutujate järjekorda saate muuta valikuga. Allpool on toodud vanuse_ruut kohe vanuse järel.
COLUMNS = ['age', 'age_square', 'workclass', 'fnlwgt', 'education', 'education_num', 'marital',
'occupation', 'relationship', 'race', 'sex', 'capital_gain', 'capital_loss',
'hours_week', 'native_country', 'label']
df = df.select(COLUMNS)
df.first()
Row(age=39, age_square=1521.0, workclass='State-gov', fnlwgt=77516, education='Bachelors', education_num=13, marital='Never-married', occupation='Adm-clerical', relationship='Not-in-family', race='White', sex='Male', capital_gain=2174, capital_loss=0, hours_week=40, native_country='United-States', label='<=50K')
Välista Holland-Holland
Kui objekti rühmal on ainult üks vaatlus, ei too see mudelisse teavet. Vastupidi, see võib ristvalideerimisel põhjustada tõrke.
Kontrollime leibkonna päritolu
df.filter(df.native_country == 'Holand-Netherlands').count()
df.groupby('native_country').agg({'native_country': 'count'}).sort(asc("count(native_country)")).show()
+--------------------+---------------------+ | native_country|count(native_country)| +--------------------+---------------------+ | Holand-Netherlands| 1| | Scotland| 12| | Hungary| 13| | Honduras| 13| |Outlying-US(Guam-...| 14| | Yugoslavia| 16| | Thailand| 18| | Laos| 18| | Cambodia| 19| | Trinadad&Tobago| 19| | Hong| 20| | Ireland| 24| | Ecuador| 28| | Greece| 29| | France| 29| | Peru| 31| | Nicaragua| 34| | Portugal| 37| | Iran| 43| | Haiti| 44| +--------------------+---------------------+ only showing top 20 rows
Funktsioonil native_country on ainult üks Hollandist pärit leibkond. Sa välistad selle.
df_remove = df.filter(df.native_country != 'Holand-Netherlands')
3. samm) looge andmetöötluse torujuhe
Sarnaselt scikit-learnile on Pysparkil torujuhtme API.
Torujuhe on andmete struktuuri säilitamiseks väga mugav. Lükkate andmed torujuhtmesse. Konveieri sees tehakse erinevaid toiminguid, väljundit kasutatakse algoritmi söötmiseks.
Näiteks üks masinõppe universaalne teisendus seisneb stringi teisendamises üheks kuumaks kodeerijaks, st rühma kaupa üheks veeruks. Üks kuum kodeerija on tavaliselt nulli täis maatriks.
Andmete teisendamise sammud on väga sarnased scikit-learniga. Peate:
- Indekseerige string numbriliseks
- Looge üks kuum kodeerija
- Muutke andmed
Seda tööd teevad kaks API-d: StringIndexer, OneHotEncoder
- Kõigepealt valite indekseerimiseks stringi veeru. InputCol on andmestiku veeru nimi. outputCol on teisendatud veerule antud uus nimi.
StringIndexer(inputCol="workclass", outputCol="workclass_encoded")
- Paigaldage andmed ja teisendage need
model = stringIndexer.fit(df) `indexed = model.transform(df)``
- Looge rühma põhjal uudiste veerud. Näiteks kui funktsioonis on 10 rühma, on uuel maatriksil 10 veergu, üks iga rühma kohta.
OneHotEncoder(dropLast=False, inputCol="workclassencoded", outputCol="workclassvec")
### Example encoder from pyspark.ml.feature import StringIndexer, OneHotEncoder, VectorAssembler stringIndexer = StringIndexer(inputCol="workclass", outputCol="workclass_encoded") model = stringIndexer.fit(df) indexed = model.transform(df) encoder = OneHotEncoder(dropLast=False, inputCol="workclass_encoded", outputCol="workclass_vec") encoded = encoder.transform(indexed) encoded.show(2)
+---+----------+----------------+------+---------+-------------+------------------+---------------+-------------+-----+----+------------+------------+----------+--------------+-----+-----------------+-------------+ |age|age_square| workclass|fnlwgt|education|education_num| marital| occupation| relationship| race| sex|capital_gain|capital_loss|hours_week|native_country|label|workclass_encoded|workclass_vec| +---+----------+----------------+------+---------+-------------+------------------+---------------+-------------+-----+----+------------+------------+----------+--------------+-----+-----------------+-------------+ | 39| 1521.0| State-gov| 77516|Bachelors| 13| Never-married| Adm-clerical|Not-in-family|White|Male| 2174| 0| 40| United-States|<=50K| 4.0|(9,[4],[1.0])| | 50| 2500.0|Self-emp-not-inc| 83311|Bachelors| 13|Married-civ-spouse|Exec-managerial| Husband|White|Male| 0| 0| 13| United-States|<=50K| 1.0|(9,[1],[1.0])| +---+----------+----------------+------+---------+-------------+------------------+---------------+-------------+-----+----+------------+------------+----------+--------------+-----+-----------------+-------------+ only showing top 2 rows
Ehitage torujuhe
Ehitate konveieri kõigi täpsete funktsioonide teisendamiseks ja lisate need lõplikku andmekogumisse. Konveieril on neli toimingut, kuid võite vabalt lisada nii palju toiminguid, kui soovite.
- Kodeerige kategoorilised andmed
- Indekseerige sildi funktsioon
- Lisa pidev muutuja
- Pange astmed kokku.
Iga samm salvestatakse loendisse, mille nimi on etapid. See loend ütleb VectorAssemblerile, milliseid toiminguid konveieri sees teha.
1. Kodeerige kategoorilised andmed
See samm on täpselt sama, mis ülaltoodud näide, välja arvatud see, et teete silmuse üle kõigi kategooriliste tunnuste.
from pyspark.ml import Pipeline
from pyspark.ml.feature import OneHotEncoderEstimator
CATE_FEATURES = ['workclass', 'education', 'marital', 'occupation', 'relationship', 'race', 'sex', 'native_country']
stages = [] # stages in our Pipeline
for categoricalCol in CATE_FEATURES:
stringIndexer = StringIndexer(inputCol=categoricalCol, outputCol=categoricalCol + "Index")
encoder = OneHotEncoderEstimator(inputCols=[stringIndexer.getOutputCol()],
outputCols=[categoricalCol + "classVec"])
stages += [stringIndexer, encoder]
2. Indekseerige sildi funktsioon
Spark, nagu paljud teised teegid, ei aktsepteeri sildi jaoks stringiväärtusi. Teisendate sildi funktsiooni StringIndexeriga ja lisate selle loendi etappidele
# Convert label into label indices using the StringIndexer label_stringIdx = StringIndexer(inputCol="label", outputCol="newlabel") stages += [label_stringIdx]
3. Lisa pidev muutuja
VectorAssembleri inputCols on veergude loend. Saate luua uue loendi, mis sisaldab kõiki uusi veerge. Allolev kood täidab loendi kodeeritud kategooriliste ja pidevate funktsioonidega.
assemblerInputs = [c + "classVec" for c in CATE_FEATURES] + CONTI_FEATURES
4. Pange astmed kokku.
Lõpuks läbite kõik VectorAssembleri sammud
assembler = VectorAssembler(inputCols=assemblerInputs, outputCol="features")stages += [assembler]
Nüüd, kui kõik sammud on valmis, lükkate andmed konveierisse.
# Create a Pipeline. pipeline = Pipeline(stages=stages) pipelineModel = pipeline.fit(df_remove) model = pipelineModel.transform(df_remove)
Kui kontrollite uut andmestikku, näete, et see sisaldab kõiki funktsioone, nii muudetud kui ka muutmata. Teid huvitavad ainult uus silt ja funktsioonid. Funktsioonid hõlmavad kõiki teisendatud funktsioone ja pidevaid muutujaid.
model.take(1)
[Row(age=39, age_square=1521.0, workclass='State-gov', fnlwgt=77516, education='Bachelors', education_num=13, marital='Never-married', occupation='Adm-clerical', relationship='Not-in-family', race='White', sex='Male', capital_gain=2174, capital_loss=0, hours_week=40, native_country='United-States', label='<=50K', workclassIndex=4.0, workclassclassVec=SparseVector(8, {4: 1.0}), educationIndex=2.0, educationclassVec=SparseVector(15, {2: 1.0}), maritalIndex=1.0, maritalclassVec=SparseVector(6, {1: 1.0}), occupationIndex=3.0, occupationclassVec=SparseVector(14, {3: 1.0}), relationshipIndex=1.0, relationshipclassVec=SparseVector(5, {1: 1.0}), raceIndex=0.0, raceclassVec=SparseVector(4, {0: 1.0}), sexIndex=0.0, sexclassVec=SparseVector(1, {0: 1.0}), native_countryIndex=0.0, native_countryclassVec=SparseVector(40, {0: 1.0}), newlabel=0.0, features=SparseVector(99, {4: 1.0, 10: 1.0, 24: 1.0, 32: 1.0, 44: 1.0, 48: 1.0, 52: 1.0, 53: 1.0, 93: 39.0, 94: 77516.0, 95: 2174.0, 96: 13.0, 98: 40.0}))]
4. samm) Looge klassifikaator: logistiline
Arvutamise kiirendamiseks teisendate mudeli DataFrame'iks.
Peate valima kaardi abil mudelist uue sildi ja funktsioonid.
from pyspark.ml.linalg import DenseVector input_data = model.rdd.map(lambda x: (x["newlabel"], DenseVector(x["features"])))
Olete valmis rongiandmed DataFrame'ina looma. Kasutate sqlContexti
df_train = sqlContext.createDataFrame(input_data, ["label", "features"])
Kontrollige teist rida
df_train.show(2)
+-----+--------------------+ |label| features| +-----+--------------------+ | 0.0|[0.0,0.0,0.0,0.0,...| | 0.0|[0.0,1.0,0.0,0.0,...| +-----+--------------------+ only showing top 2 rows
Looge rongi-/katsekomplekt
Jagate andmestiku 80/20 juhusliku jaotusega.
# Split the data into train and test sets train_data, test_data = df_train.randomSplit([.8,.2],seed=1234)
Loeme kokku, kui palju inimesi, kelle sissetulek on alla/üle 50k nii koolitusel kui ka testikomplektis
train_data.groupby('label').agg({'label': 'count'}).show()
+-----+------------+ |label|count(label)| +-----+------------+ | 0.0| 19698| | 1.0| 6263| +-----+------------+
test_data.groupby('label').agg({'label': 'count'}).show()
+-----+------------+ |label|count(label)| +-----+------------+ | 0.0| 5021| | 1.0| 1578| +-----+------------+
Looge logistiline regressor
Viimaseks, kuid mitte vähemtähtsaks, saate koostada klassifikaatori. Pysparkil on logistilise regressiooni teostamiseks API nimega LogisticRegression.
Lr lähtestatakse, näidates sildi veeru ja funktsioonide veerud. Määrate maksimaalselt 10 iteratsiooni ja lisate reguleerimisparameetri väärtusega 0.3. Pange tähele, et järgmises jaotises kasutate mudeli häälestamiseks ristvalideerimist parameetrite ruudustikuga
# Import `LinearRegression`
from pyspark.ml.classification import LogisticRegression
# Initialize `lr`
lr = LogisticRegression(labelCol="label",
featuresCol="features",
maxIter=10,
regParam=0.3)
# Fit the data to the model
linearModel = lr.fit(train_data)
#Koefitsiente näete regressioonist
# Print the coefficients and intercept for logistic regression
print("Coefficients: " + str(linearModel.coefficients))
print("Intercept: " + str(linearModel.intercept))
Coefficients: [-0.0678914665262,-0.153425526813,-0.0706009536407,-0.164057586562,-0.120655298528,0.162922330862,0.149176870438,-0.626836362611,-0.193483661541,-0.0782269980838,0.222667203836,0.399571096381,-0.0222024341804,-0.311925857859,-0.0434497788688,-0.306007744328,-0.41318209688,0.547937504247,-0.395837350854,-0.23166535958,0.618743906733,-0.344088614546,-0.385266881369,0.317324463006,-0.350518889186,-0.201335923138,-0.232878560088,-0.13349278865,-0.119760542498,0.17500602491,-0.0480968101118,0.288484253943,-0.116314616745,0.0524163478063,-0.300952624551,-0.22046421474,-0.16557996579,-0.114676231939,-0.311966431453,-0.344226119233,0.105530129507,0.152243047814,-0.292774545497,0.263628334433,-0.199951374076,-0.30329422583,-0.231087515178,0.418918551,-0.0565930184279,-0.177818073048,-0.0733236680663,-0.267972912252,0.168491215697,-0.12181255723,-0.385648075442,-0.202101794517,0.0469791640782,-0.00842850210625,-0.00373211448629,-0.259296141281,-0.309896554133,-0.168434409756,-0.11048086026,0.0280647963877,-0.204187030092,-0.414392623536,-0.252806580669,0.143366465705,-0.516359222663,-0.435627370849,-0.301949286524,0.0878249035894,-0.210951740965,-0.621417928742,-0.099445190784,-0.232671473401,-0.1077745606,-0.360429419703,-0.420362959052,-0.379729467809,-0.395186242741,0.0826401853838,-0.280251589972,0.187313505214,-0.20295228799,-0.431177064626,0.149759018379,-0.107114299614,-0.319314858424,0.0028450133235,-0.651220387649,-0.327918792207,-0.143659581445,0.00691075160413,8.38517628783e-08,2.18856717378e-05,0.0266701216268,0.000231075966823,0.00893832698698] Intercept: -1.9884177974805692
5. samm) Treenige ja hinnake mudelit
Testikomplekti ennustuse loomiseks
Saate kasutada linearModelit koos transform()-ga test_data
# Make predictions on test data using the transform() method. predictions = linearModel.transform(test_data)
Saate printida ennustustes olevad elemendid
predictions.printSchema() root |-- label: double (nullable = true) |-- features: vector (nullable = true) |-- rawPrediction: vector (nullable = true) |-- probability: vector (nullable = true) |-- prediction: double (nullable = false)
Teid huvitavad silt, ennustus ja tõenäosus
selected = predictions.select("label", "prediction", "probability")
selected.show(20)
+-----+----------+--------------------+ |label|prediction| probability| +-----+----------+--------------------+ | 0.0| 0.0|[0.91560704124179...| | 0.0| 0.0|[0.92812140213994...| | 0.0| 0.0|[0.92161406774159...| | 0.0| 0.0|[0.96222760777142...| | 0.0| 0.0|[0.66363283056957...| | 0.0| 0.0|[0.65571324475477...| | 0.0| 0.0|[0.73053376932829...| | 0.0| 1.0|[0.31265053873570...| | 0.0| 0.0|[0.80005907577390...| | 0.0| 0.0|[0.76482251301640...| | 0.0| 0.0|[0.84447301189069...| | 0.0| 0.0|[0.75691912026619...| | 0.0| 0.0|[0.60902504096722...| | 0.0| 0.0|[0.80799228385509...| | 0.0| 0.0|[0.87704364852567...| | 0.0| 0.0|[0.83817652582377...| | 0.0| 0.0|[0.79655423248500...| | 0.0| 0.0|[0.82712311232246...| | 0.0| 0.0|[0.81372823882016...| | 0.0| 0.0|[0.59687710752201...| +-----+----------+--------------------+ only showing top 20 rows
Hinnake mudelit
Peate vaatama täpsuse mõõdikut, et näha, kui hästi (või halvasti) mudel toimib. Praegu pole API-d täpsuse mõõtmiseks Spark. Vaikeväärtus on ROC, vastuvõtja tööomaduste kõver. See on teistsugune mõõdik, mis võtab arvesse valepositiivsete tulemuste määra.
Enne ROC-i vaatamist konstrueerime täpsuse mõõdiku. Olete selle mõõdikuga rohkem tuttav. Täpsusmõõt on õige ennustuse summa vaatluste koguarvust.
Loote DataFrame'i sildi ja ennustusega.
cm = predictions.select("label", "prediction")
Saate kontrollida klasside arvu etiketil ja ennustuses
cm.groupby('label').agg({'label': 'count'}).show()
+-----+------------+ |label|count(label)| +-----+------------+ | 0.0| 5021| | 1.0| 1578| +-----+------------+
cm.groupby('prediction').agg({'prediction': 'count'}).show()
+----------+-----------------+ |prediction|count(prediction)| +----------+-----------------+ | 0.0| 5982| | 1.0| 617| +----------+-----------------+
Näiteks on testikomplektis 1578 leibkonda, kelle sissetulek on üle 50 5021 ja 617 väiksem. Klassifikaator ennustas aga 50 leibkonda, kelle sissetulek oli üle XNUMX XNUMX.
Kui silt on ridade koguarvust õigesti liigitatud, saate täpsuse arvutada.
cm.filter(cm.label == cm.prediction).count() / cm.count()
0.8237611759357478
Saate kõik kokku panna ja täpsuse arvutamiseks funktsiooni kirjutada.
def accuracy_m(model):
predictions = model.transform(test_data)
cm = predictions.select("label", "prediction")
acc = cm.filter(cm.label == cm.prediction).count() / cm.count()
print("Model accuracy: %.3f%%" % (acc * 100))
accuracy_m(model = linearModel)
Model accuracy: 82.376%
ROC mõõdikud
Moodul BinaryClassificationEvaluator sisaldab ROC mõõdikuid. Vastuvõtja Operating Karakteristikukõver on teine levinud tööriist, mida kasutatakse binaarse klassifikatsiooni puhul. See on väga sarnane täpsuse/meenutamise kõveraga, kuid selle asemel, et joonistada täpsus versus meeldetuletus, näitab ROC kõver tõelist positiivset määra (st tagasikutsumist) valepositiivse määra suhtes. Valepositiivsuse määr on negatiivsete juhtumite suhe, mis on valesti positiivseteks liigitatud. See on võrdne ühega, millest on lahutatud tegelik negatiivne määr. Tõelist negatiivset määra nimetatakse ka spetsiifilisuseks. Seega kujutab ROC kõver tundlikkust (meenutamist) versus 1 - spetsiifilisus
### Use ROC from pyspark.ml.evaluation import BinaryClassificationEvaluator # Evaluate model evaluator = BinaryClassificationEvaluator(rawPredictionCol="rawPrediction") print(evaluator.evaluate(predictions)) print(evaluator.getMetricName())
0.8940481662695192ROC-i ala
print(evaluator.evaluate(predictions))
0.8940481662695192
6. samm) Häälestage hüperparameeter
Viimaseks, kuid mitte vähem tähtsaks, saate häälestada hüperparameetreid. Sarnased scikit õppida loote parameetrite ruudustiku ja lisate parameetrid, mida soovite häälestada.
Arvutusaja lühendamiseks häälestate ainult kahe väärtusega regulatsiooniparameetrit.
from pyspark.ml.tuning import ParamGridBuilder, CrossValidator
# Create ParamGrid for Cross Validation
paramGrid = (ParamGridBuilder()
.addGrid(lr.regParam, [0.01, 0.5])
.build())
Lõpuks hindate mudelit, kasutades ristvalideerimise meetodit 5 voldiga. Treenimiseks kulub umbes 16 minutit.
from time import *
start_time = time()
# Create 5-fold CrossValidator
cv = CrossValidator(estimator=lr,
estimatorParamMaps=paramGrid,
evaluator=evaluator, numFolds=5)
# Run cross validations
cvModel = cv.fit(train_data)
# likely take a fair amount of time
end_time = time()
elapsed_time = end_time - start_time
print("Time to train model: %.3f seconds" % elapsed_time)
Modelli treenimise aeg: 978.807 sekundit
Parim reguleerimise hüperparameeter on 0.01, täpsusega 85.316 protsenti.
accuracy_m(model = cvModel) Model accuracy: 85.316%
Soovitatud parameetri saate ekstraktida, aheldades cvModel.bestModel käsuga extractParamMap()
bestModel = cvModel.bestModel bestModel.extractParamMap()
{Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='aggregationDepth', doc='suggested depth for treeAggregate (>= 2)'): 2,
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='elasticNetParam', doc='the ElasticNet mixing parameter, in range [0, 1]. For alpha = 0, the penalty is an L2 penalty. For alpha = 1, it is an L1 penalty'): 0.0,
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='family', doc='The name of family which is a description of the label distribution to be used in the model. Supported options: auto, binomial, multinomial.'): 'auto',
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='featuresCol', doc='features column name'): 'features',
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='fitIntercept', doc='whether to fit an intercept term'): True,
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='labelCol', doc='label column name'): 'label',
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='maxIter', doc='maximum number of iterations (>= 0)'): 10,
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='predictionCol', doc='prediction column name'): 'prediction',
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='probabilityCol', doc='Column name for predicted class conditional probabilities. Note: Not all models output well-calibrated probability estimates! These probabilities should be treated as confidences, not precise probabilities'): 'probability',
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='rawPredictionCol', doc='raw prediction (a.k.a. confidence) column name'): 'rawPrediction',
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='regParam', doc='regularization parameter (>= 0)'): 0.01,
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='standardization', doc='whether to standardize the training features before fitting the model'): True,
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='threshold', doc='threshold in binary classification prediction, in range [0, 1]'): 0.5,
Param(parent='LogisticRegression_4d8f8ce4d6a02d8c29a0', name='tol', doc='the convergence tolerance for iterative algorithms (>= 0)'): 1e-06}
kokkuvõte
Spark on andmeteadlase põhitööriist. See võimaldab praktikul ühendada rakenduse erinevate andmeallikatega, teha sujuvalt andmete analüüsi või lisada ennustava mudeli.
Alustuseks Spark, peate algatama a Spark Kontekst:
"Sparkkontekst()'
ja ja SQL kontekstis andmeallikaga ühenduse loomiseks:
'SQLContext()'
Õpetusest saate teada, kuidas treenida logistilist regressiooni:
- Teisendage andmestik andmeraamiks, kasutades järgmist:
rdd.map(lambda x: (x["newlabel"], DenseVector(x["features"]))) sqlContext.createDataFrame(input_data, ["label", "features"])
Pange tähele, et sildi veeru nimi on uus silt ja kõik funktsioonid on koondatud funktsioonidesse. Muutke neid väärtusi, kui need teie andmekogus erinevad.
- Looge rongi-/katsekomplekt
randomSplit([.8,.2],seed=1234)
- Treeni modelli
LogisticRegression(labelCol="label",featuresCol="features",maxIter=10, regParam=0.3)
lr.fit()
- Tehke ennustus
linearModel.transform()

