Data Science Academy - Python Fundamentos - Capítulo 9

Download: http://github.com/dsacademybr


In [1]:
# Versão da Linguagem Python
from platform import python_version
print('Versão da Linguagem Python Usada Neste Jupyter Notebook:', python_version())


Versão da Linguagem Python Usada Neste Jupyter Notebook: 3.7.6

Análise Exploratória de Dados

Neste notebook usaremos uma pesquisa recente nos EUA sobre o mercado de trabalho para programadores de software. Nosso objetivo é fazer uma investigação inicial dos dados a fim de detectar problemas com os dados, necessidade de mais variáveis, falhas na organização e necessidades de transformação.

Pesquisa Salarial realizada pelo site https://www.freecodecamp.com/ com programadores de software nos EUA que frequentaram treinamentos Bootcamp.


In [2]:
# Importando os pacotes 
import numpy as np
import pandas as pd
import matplotlib as mat
import matplotlib.pyplot as plt
import colorsys
plt.style.use('seaborn-talk')
import warnings
warnings.filterwarnings("ignore")
%matplotlib inline

In [3]:
np.__version__


Out[3]:
'1.18.2'

In [4]:
pd.__version__


Out[4]:
'1.0.3'

In [5]:
mat.__version__


Out[5]:
'3.2.1'

In [6]:
# Carregando o dataset
df = pd.read_csv("Dados-Pesquisa.csv", sep = ',', low_memory=False)

In [7]:
print(df.head())


    Age  AttendedBootcamp  BootcampFinish  BootcampFullJobAfter  \
0  28.0               0.0             NaN                   NaN   
1  22.0               0.0             NaN                   NaN   
2  19.0               0.0             NaN                   NaN   
3  26.0               0.0             NaN                   NaN   
4  20.0               0.0             NaN                   NaN   

   BootcampLoanYesNo  BootcampMonthsAgo BootcampName  BootcampPostSalary  \
0                NaN                NaN          NaN                 NaN   
1                NaN                NaN          NaN                 NaN   
2                NaN                NaN          NaN                 NaN   
3                NaN                NaN          NaN                 NaN   
4                NaN                NaN          NaN                 NaN   

   BootcampRecommend  ChildrenNumber  ... ResourceSoloLearn  \
0                NaN             NaN  ...               NaN   
1                NaN             NaN  ...               NaN   
2                NaN             NaN  ...               NaN   
3                NaN             NaN  ...               NaN   
4                NaN             NaN  ...               NaN   

   ResourceStackOverflow  ResourceTreehouse  ResourceUdacity  ResourceUdemy  \
0                    NaN                NaN              NaN            NaN   
1                    NaN                NaN              NaN            1.0   
2                    NaN                NaN              NaN            NaN   
3                    NaN                NaN              NaN            NaN   
4                    NaN                NaN              NaN            NaN   

   ResourceW3Schools  ResourceYouTube  \
0                NaN              NaN   
1                NaN              NaN   
2                NaN              NaN   
3                NaN              NaN   
4                NaN              NaN   

                              SchoolDegree              SchoolMajor  \
0           some college credit, no degree                      NaN   
1           some college credit, no degree                      NaN   
2  high school diploma or equivalent (GED)                      NaN   
3                        bachelor's degree  Cinematography And Film   
4           some college credit, no degree                      NaN   

   StudentDebtOwe  
0         20000.0  
1             NaN  
2             NaN  
3          7000.0  
4             NaN  

[5 rows x 113 columns]

In [8]:
df


Out[8]:
Age AttendedBootcamp BootcampFinish BootcampFullJobAfter BootcampLoanYesNo BootcampMonthsAgo BootcampName BootcampPostSalary BootcampRecommend ChildrenNumber ... ResourceSoloLearn ResourceStackOverflow ResourceTreehouse ResourceUdacity ResourceUdemy ResourceW3Schools ResourceYouTube SchoolDegree SchoolMajor StudentDebtOwe
0 28.0 0.0 NaN NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN some college credit, no degree NaN 20000.0
1 22.0 0.0 NaN NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN 1.0 NaN NaN some college credit, no degree NaN NaN
2 19.0 0.0 NaN NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN high school diploma or equivalent (GED) NaN NaN
3 26.0 0.0 NaN NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN bachelor's degree Cinematography And Film 7000.0
4 20.0 0.0 NaN NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN some college credit, no degree NaN NaN
... ... ... ... ... ... ... ... ... ... ... ... ... ... ... ... ... ... ... ... ... ...
15615 39.0 0.0 NaN NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN 1.0 NaN NaN bachelor's degree Chemistry NaN
15616 27.0 0.0 NaN NaN NaN NaN NaN NaN NaN NaN ... NaN NaN 1.0 NaN NaN NaN NaN bachelor's degree Electrical Engineering NaN
15617 37.0 0.0 NaN NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN bachelor's degree Chemistry NaN
15618 26.0 0.0 NaN NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN 1.0 NaN NaN master's degree (non-professional) Math NaN
15619 22.0 0.0 NaN NaN NaN NaN NaN NaN NaN NaN ... NaN NaN NaN NaN NaN NaN NaN bachelor's degree Graphic Design 40000.0

15620 rows × 113 columns


In [9]:
print(df.describe())


                Age  AttendedBootcamp  BootcampFinish  BootcampFullJobAfter  \
count  13613.000000      15380.000000      933.000000            635.000000   
mean      29.175421          0.061964        0.689175              0.584252   
std        9.017716          0.241097        0.463080              0.493239   
min       10.000000          0.000000        0.000000              0.000000   
25%       23.000000          0.000000        0.000000              0.000000   
50%       27.000000          0.000000        1.000000              1.000000   
75%       33.000000          0.000000        1.000000              1.000000   
max       86.000000          1.000000        1.000000              1.000000   

       BootcampLoanYesNo  BootcampMonthsAgo  BootcampPostSalary  \
count         934.000000         631.000000          330.000000   
mean            0.332976           9.055468        63740.506061   
std             0.471531          12.968035        26347.200265   
min             0.000000           0.000000         6000.000000   
25%             0.000000           3.000000        50000.000000   
50%             0.000000           6.000000        60000.000000   
75%             1.000000          12.000000        77000.000000   
max             1.000000         220.000000       200000.000000   

       BootcampRecommend  ChildrenNumber  CodeEventBootcamp  ...  \
count         937.000000     2554.000000               42.0  ...   
mean            0.785486        1.896241                1.0  ...   
std             0.410704        1.115975                0.0  ...   
min             0.000000        0.000000                1.0  ...   
25%             1.000000        1.000000                1.0  ...   
50%             1.000000        2.000000                1.0  ...   
75%             1.000000        2.000000                1.0  ...   
max             1.000000       18.000000                1.0  ...   

       ResourceReddit  ResourceSkillCrush  ResourceSoloLearn  \
count            29.0                36.0               30.0   
mean              1.0                 1.0                1.0   
std               0.0                 0.0                0.0   
min               1.0                 1.0                1.0   
25%               1.0                 1.0                1.0   
50%               1.0                 1.0                1.0   
75%               1.0                 1.0                1.0   
max               1.0                 1.0                1.0   

       ResourceStackOverflow  ResourceTreehouse  ResourceUdacity  \
count                  191.0              422.0           3306.0   
mean                     1.0                1.0              1.0   
std                      0.0                0.0              0.0   
min                      1.0                1.0              1.0   
25%                      1.0                1.0              1.0   
50%                      1.0                1.0              1.0   
75%                      1.0                1.0              1.0   
max                      1.0                1.0              1.0   

       ResourceUdemy  ResourceW3Schools  ResourceYouTube  StudentDebtOwe  
count         4130.0              121.0            121.0     3514.000000  
mean             1.0                1.0              1.0    34556.143711  
std              0.0                0.0              0.0    54423.139781  
min              1.0                1.0              1.0        0.000000  
25%              1.0                1.0              1.0    10000.000000  
50%              1.0                1.0              1.0    20000.000000  
75%              1.0                1.0              1.0    40000.000000  
max              1.0                1.0              1.0  1000000.000000  

[8 rows x 85 columns]

In [10]:
# Lista todas as colunas
list(df)


Out[10]:
['Age',
 'AttendedBootcamp',
 'BootcampFinish',
 'BootcampFullJobAfter',
 'BootcampLoanYesNo',
 'BootcampMonthsAgo',
 'BootcampName',
 'BootcampPostSalary',
 'BootcampRecommend',
 'ChildrenNumber',
 'CityPopulation',
 'CodeEventBootcamp',
 'CodeEventCoffee',
 'CodeEventConferences',
 'CodeEventDjangoGirls',
 'CodeEventGameJam',
 'CodeEventGirlDev',
 'CodeEventHackathons',
 'CodeEventMeetup',
 'CodeEventNodeSchool',
 'CodeEventNone',
 'CodeEventOther',
 'CodeEventRailsBridge',
 'CodeEventRailsGirls',
 'CodeEventStartUpWknd',
 'CodeEventWomenCode',
 'CodeEventWorkshop',
 'CommuteTime',
 'CountryCitizen',
 'CountryLive',
 'EmploymentField',
 'EmploymentFieldOther',
 'EmploymentStatus',
 'EmploymentStatusOther',
 'ExpectedEarning',
 'FinanciallySupporting',
 'Gender',
 'HasChildren',
 'HasDebt',
 'HasFinancialDependents',
 'HasHighSpdInternet',
 'HasHomeMortgage',
 'HasServedInMilitary',
 'HasStudentDebt',
 'HomeMortgageOwe',
 'HoursLearning',
 'ID.x',
 'ID.y',
 'Income',
 'IsEthnicMinority',
 'IsReceiveDiabilitiesBenefits',
 'IsSoftwareDev',
 'IsUnderEmployed',
 'JobApplyWhen',
 'JobPref',
 'JobRelocateYesNo',
 'JobRoleInterest',
 'JobRoleInterestOther',
 'JobWherePref',
 'LanguageAtHome',
 'MaritalStatus',
 'MoneyForLearning',
 'MonthsProgramming',
 'NetworkID',
 'Part1EndTime',
 'Part1StartTime',
 'Part2EndTime',
 'Part2StartTime',
 'PodcastChangeLog',
 'PodcastCodeNewbie',
 'PodcastCodingBlocks',
 'PodcastDeveloperTea',
 'PodcastDotNetRocks',
 'PodcastHanselminutes',
 'PodcastJSJabber',
 'PodcastJsAir',
 'PodcastNone',
 'PodcastOther',
 'PodcastProgrammingThrowDown',
 'PodcastRubyRogues',
 'PodcastSEDaily',
 'PodcastShopTalk',
 'PodcastTalkPython',
 'PodcastWebAhead',
 'ResourceBlogs',
 'ResourceBooks',
 'ResourceCodeWars',
 'ResourceCodecademy',
 'ResourceCoursera',
 'ResourceDevTips',
 'ResourceEdX',
 'ResourceEggHead',
 'ResourceFCC',
 'ResourceGoogle',
 'ResourceHackerRank',
 'ResourceKhanAcademy',
 'ResourceLynda',
 'ResourceMDN',
 'ResourceOdinProj',
 'ResourceOther',
 'ResourcePluralSight',
 'ResourceReddit',
 'ResourceSkillCrush',
 'ResourceSoloLearn',
 'ResourceStackOverflow',
 'ResourceTreehouse',
 'ResourceUdacity',
 'ResourceUdemy',
 'ResourceW3Schools',
 'ResourceYouTube',
 'SchoolDegree',
 'SchoolMajor',
 'StudentDebtOwe']

Distribuição de Idade


In [11]:
# Qual a distribuição de idade dos participantes da pesquisa?
# A maioria dos profissionais que trabalham como programadores de 
# software estão na faixa de idade entre 20 e 30 anos, sendo 25 anos 
# a idade mais frequente.

# Gerando um histograma
df.Age.hist(bins = 60)
plt.xlabel("Idade")
plt.ylabel("Número de Profissionais")
plt.title("Distribuição de Idade")
plt.show()


Distribuição de Sexo


In [12]:
# Qual é a distribuição de sexo dos participantes da pesquisa?
# A grande maioria dos programadores é do sexo masculino

# Definindo a quantidade
labels = df.Gender.value_counts().index
num = len(df.EmploymentField.value_counts().index)

# Criando a lista de cores
listaHSV = [(x*1.0/num, 0.5, 0.5) for x in range(num)]
listaRGB = list(map(lambda x: colorsys.hsv_to_rgb(*x), listaHSV))

# Gráfico de Pizza
fatias, texto = plt.pie(df.Gender.value_counts(), colors = listaRGB, startangle = 90)
plt.axes().set_aspect('equal', 'datalim')
plt.legend(fatias, labels, bbox_to_anchor = (1.05,1))
plt.title("Sexo")
plt.show()


Distribuição de Interesses


In [13]:
# Quais sãos os principais interesses dos participantes da pesquisa?
# O principal interesse profissional dos programadores é o desenvolvimento web (Full-Stack, Front-End e Back-End), 
# seguido pela área de Data Science.

# Definindo a quantidade
num = len(df.JobRoleInterest.value_counts().index)

# Criando a lista de cores
listaHSV = [(x*1.0/num, 0.5, 0.5) for x in range(num)]
listaRGB = list(map(lambda x: colorsys.hsv_to_rgb(*x), listaHSV))
labels = df.JobRoleInterest.value_counts().index
colors = ['OliveDrab', 'Orange', 'OrangeRed', 'DarkCyan', 'Salmon', 'Sienna', 'Maroon', 'LightSlateGrey', 'DimGray']

# Gráfico de Pizza
fatias, texto = plt.pie(df.JobRoleInterest.value_counts(), colors = listaRGB, startangle = 90)
plt.axes().set_aspect('equal', 'datalim')
plt.legend(fatias, labels, bbox_to_anchor = (1.25, 1))
plt.title("Interesse Profissional")
plt.show()


Distribuição de Empregabilidade


In [14]:
# Quais as áreas de negócio em que os participantes da pesquisa trabalham?
# A maioria dos programadores trabalha na área de desenvolvimento de 
# softwares e TI, mas outras áreas como finanças e saúde também são 
# significativas.

# Definindo a quantidade
num = len(df.EmploymentField.value_counts().index)

# Criando a lista de cores
listaHSV = [(x*1.0/num, 0.5, 0.5) for x in range(num)]
listaRGB = list(map(lambda x: colorsys.hsv_to_rgb(*x), listaHSV))
labels = df.EmploymentField.value_counts().index

# Gráfico de Pizza
fatias, texto = plt.pie(df.EmploymentField.value_counts(), colors = listaRGB, startangle = 90)
plt.axes().set_aspect('equal', 'datalim')
plt.legend(fatias, labels, bbox_to_anchor = (1.3, 1))
plt.title("Área de trabalho Atual")
plt.show()


Preferências de Trabalho por Idade


In [15]:
# Quais são as preferências de trabalho por idade?
# Perceba que à medida que a idade aumenta, o interesse por trabalho 
# freelance também aumenta, sendo o modelo preferido por profissionais 
# acima de 60 anos. Profissionais mais jovens preferem trabalhar em 
# Startups ou no seu próprio negócio. Profissionais entre 20 e 50 anos 
# preferem trabalhar em empresas de tamanho médio.

# Agrupando os dados
df_ageranges = df.copy()
bins=[0, 20, 30, 40, 50, 60, 100]

df_ageranges['AgeRanges'] = pd.cut(df_ageranges['Age'], 
                                   bins, 
                                   labels=["< 20", "20-30", "30-40", "40-50", "50-60", "< 60"]) 

df2 = pd.crosstab(df_ageranges.AgeRanges, 
                  df_ageranges.JobPref).apply(lambda r: r/r.sum(), axis=1)

# Definindo a quantidade
num = len(df_ageranges.AgeRanges.value_counts().index)

# Criando a lista de cores
listaHSV = [(x*1.0/num, 0.5, 0.5) for x in range(num)]
listaRGB = list(map(lambda x: colorsys.hsv_to_rgb(*x), listaHSV))

# Gráfico de Barras (Stacked)
ax1 = df2.plot(kind = "bar", stacked = True, color = listaRGB, title = "Preferência de Trabalho por Idade")
lines, labels = ax1.get_legend_handles_labels()
ax1.legend(lines, labels, bbox_to_anchor = (1.51, 1))


Out[15]:
<matplotlib.legend.Legend at 0x7fdff12a87d0>

In [16]:
# Visualizando o help
help(pd.crosstab)


Help on function crosstab in module pandas.core.reshape.pivot:

crosstab(index, columns, values=None, rownames=None, colnames=None, aggfunc=None, margins=False, margins_name: str = 'All', dropna: bool = True, normalize=False) -> 'DataFrame'
    Compute a simple cross tabulation of two (or more) factors. By default
    computes a frequency table of the factors unless an array of values and an
    aggregation function are passed.
    
    Parameters
    ----------
    index : array-like, Series, or list of arrays/Series
        Values to group by in the rows.
    columns : array-like, Series, or list of arrays/Series
        Values to group by in the columns.
    values : array-like, optional
        Array of values to aggregate according to the factors.
        Requires `aggfunc` be specified.
    rownames : sequence, default None
        If passed, must match number of row arrays passed.
    colnames : sequence, default None
        If passed, must match number of column arrays passed.
    aggfunc : function, optional
        If specified, requires `values` be specified as well.
    margins : bool, default False
        Add row/column margins (subtotals).
    margins_name : str, default 'All'
        Name of the row/column that will contain the totals
        when margins is True.
    
        .. versionadded:: 0.21.0
    
    dropna : bool, default True
        Do not include columns whose entries are all NaN.
    normalize : bool, {'all', 'index', 'columns'}, or {0,1}, default False
        Normalize by dividing all values by the sum of values.
    
        - If passed 'all' or `True`, will normalize over all values.
        - If passed 'index' will normalize over each row.
        - If passed 'columns' will normalize over each column.
        - If margins is `True`, will also normalize margin values.
    
    Returns
    -------
    DataFrame
        Cross tabulation of the data.
    
    See Also
    --------
    DataFrame.pivot : Reshape data based on column values.
    pivot_table : Create a pivot table as a DataFrame.
    
    Notes
    -----
    Any Series passed will have their name attributes used unless row or column
    names for the cross-tabulation are specified.
    
    Any input passed containing Categorical data will have **all** of its
    categories included in the cross-tabulation, even if the actual data does
    not contain any instances of a particular category.
    
    In the event that there aren't overlapping indexes an empty DataFrame will
    be returned.
    
    Examples
    --------
    >>> a = np.array(["foo", "foo", "foo", "foo", "bar", "bar",
    ...               "bar", "bar", "foo", "foo", "foo"], dtype=object)
    >>> b = np.array(["one", "one", "one", "two", "one", "one",
    ...               "one", "two", "two", "two", "one"], dtype=object)
    >>> c = np.array(["dull", "dull", "shiny", "dull", "dull", "shiny",
    ...               "shiny", "dull", "shiny", "shiny", "shiny"],
    ...              dtype=object)
    >>> pd.crosstab(a, [b, c], rownames=['a'], colnames=['b', 'c'])
    b   one        two
    c   dull shiny dull shiny
    a
    bar    1     2    1     0
    foo    2     2    1     2
    
    Here 'c' and 'f' are not represented in the data and will not be
    shown in the output because dropna is True by default. Set
    dropna=False to preserve categories with no data.
    
    >>> foo = pd.Categorical(['a', 'b'], categories=['a', 'b', 'c'])
    >>> bar = pd.Categorical(['d', 'e'], categories=['d', 'e', 'f'])
    >>> pd.crosstab(foo, bar)
    col_0  d  e
    row_0
    a      1  0
    b      0  1
    >>> pd.crosstab(foo, bar, dropna=False)
    col_0  d  e  f
    row_0
    a      1  0  0
    b      0  1  0
    c      0  0  0

Realocação por Idade


In [17]:
# Qual o objetivo de realocação?
# A vontade de buscar um novo emprego diminui com a idade. 
# Quase 80% das pessoas abaixo dos 30 anos estão preparadas para isso.

# Agrupando os dados
df3 = pd.crosstab(df_ageranges.AgeRanges, 
                  df_ageranges.JobRelocateYesNo).apply(lambda r: r/r.sum(), axis = 1)

# Definindo a quantidade
num = len(df_ageranges.AgeRanges.value_counts().index)

# Criando a lista de cores
listaHSV = [(x*1.0/num, 0.5, 0.5) for x in range(num)]
listaRGB = list(map(lambda x: colorsys.hsv_to_rgb(*x), listaHSV))

# Gráfico de Barras (Stacked)
ax1 = df3.plot(kind = "bar", stacked = True, color = listaRGB, title = "Realocação por Idade")
lines, labels = ax1.get_legend_handles_labels()
ax1.legend(lines,["Não", "Sim"], loc = 'best')


Out[17]:
<matplotlib.legend.Legend at 0x7fdff129cd50>

Idade x Horas de Aprendizagem


In [18]:
# Qual a relação entre idade e horas de aprendizagem?
# A idade dos profissionais não afeta a quantidade de tempo gasto com capacitação e treinamento.

import warnings
warnings.filterwarnings('ignore')

# Criando subset dos dados
df9 = df.copy()
df9 = df9.dropna(subset=["HoursLearning"])
df9 = df9[df['Age'].isin(range(0,70))]

# Definindo os valores de x e y
x = df9.Age
y = df9.HoursLearning

# Computando os valores e gerando o gráfico
m, b = np.polyfit(x, y, 1)
plt.plot(x, y, '.')
plt.plot(x, m*x + b, '-', color = "red")
plt.xlabel("Idade")
plt.ylabel("Horas de Treinamento")
plt.title("Idade por Horas de Treinamento")
plt.show()


Investimento em Capacitação x Expectativa Salarial


In [19]:
# Qual a relação entre investimento em capacitação e expectativa salarial?
# Os profissionais que investem tempo e dinheiro em capacitação e 
# treinamento, em geral, conseguem salários mais altos, embora alguns 
# profisisonais esperem altos salários, investindo 0 em treinamento.

import warnings
warnings.filterwarnings('ignore')

# Criando subset dos dados
df5 = df.copy()
df5 = df5.dropna(subset=["ExpectedEarning"])
df5 = df5[df['MoneyForLearning'].isin(range(0,60000))]

# Definindo os valores de x e y
x = df5.MoneyForLearning
y = df5.ExpectedEarning

# Computando os valores e gerando o gráfico
m, b = np.polyfit(x, y, 1)
plt.plot(x, y, '.')
plt.plot(x, m*x + b, '-', color = "red")
plt.xlabel("Investimento em Treinamento")
plt.ylabel("Expectativa Salarial")
plt.title("Investimento em Treinamento vs Expectativa Salarial")
plt.show()


Conheça a Formação Cientista de Dados, um programa completo, 100% online e 100% em português, com 400 horas, mais de 1.200 aulas em vídeos e 26 projetos, que vão ajudá-lo a se tornar um dos profissionais mais cobiçados do mercado de análise de dados. Clique no link abaixo, faça sua inscrição, comece hoje mesmo e aumente sua empregabilidade:

https://www.datascienceacademy.com.br/pages/formacao-cientista-de-dados

Fim

Obrigado - Data Science Academy - facebook.com/dsacademybr