<SYSTEM_TASK:>
Given the following text description, write Python code to implement the functionality described below step by step
<END_TASK>
<USER_TASK:>
Description:
 Position and Label Based Indexing
Step1:  Position (Integer) Based Indexing
Pandas provides the df.iloc functionality to index dataframes using integer indices.
Step2:  As mentioned in the documentation, the inputs x, y to df.iloc[x, y] can be
Step3:  Note that simply writing df[2, 4] will throw an error, since pandas gets confused whether the 2 is an integer index (the third row), or is it a row with label = 2? 
On the other hand, df.iloc[2, 4] tells pandas explicitly that it should assume integer indices.
Step4:  To summarise, df.iloc[x, y] uses integer indices starting at 0.
The other common way of indexing is the label based indexing, which uses df.loc[]. 
Label Based Indexing
Pandas provides the df.loc[] functionality to index dataframes using labels.
Step5:  As mentioned in the documentation, the inputs x, y to df.loc[x, y] can be
<ASSISTANT_TASK:>
Python Code:
# loading libraries and reading the data
import numpy as np
import pandas as pd
market_df = pd.read_csv("../global_sales_data/market_fact.csv")
market_df.head()
Explanation: Position and Label Based Indexing: df.iloc and df.loc
You have seen some ways of selecting rows and columns from dataframes. Let's now see some other ways of indexing dataframes, which pandas recommends, since they are more explicit (and less ambiguous).
There are two main ways of indexing dataframes:
1. Position based indexing using df.iloc
2. Label based indexing using df.loc
Using both the methods, we will do the following indexing operations on a dataframe:
* Selecting single elements/cells
* Selecting single and multiple rows
* Selecting single and multiple columns
* Selecting multiple rows and columns
End of explanation
help(pd.DataFrame.iloc)
Explanation: Position (Integer) Based Indexing
Pandas provides the df.iloc functionality to index dataframes using integer indices.
End of explanation
# Selecting a single element
# Note that 2, 4 corresponds to the third row and fifth column (Sales)
market_df.iloc[2, 4]
Explanation: As mentioned in the documentation, the inputs x, y to df.iloc[x, y] can be:
* An integer, e.g. 3
* A list or array of integers, e.g. [3, 7, 8]
* An integer range, i.e. 3:8
* A boolean array
Let's see some examples.
End of explanation
# Selecting a single row, and all columns
# Select the 6th row, with label (and index) = 5
market_df.iloc[5]
# The above is equivalent to this
# The ":" indicates "all rows/columns"
market_df.iloc[5, :]
# equivalent to market_df.iloc[5, ]
# Select multiple rows using a list of indices
market_df.iloc[[3, 7, 8]]
# Equivalently, you can use:
market_df.iloc[[3, 7, 8], :]
# same as market_df.iloc[[3, 7, 8], ]
# Selecting rows using a range of integer indices
# Notice that 4 is included, 8 is not
market_df.iloc[4:8]
# or equivalently
market_df.iloc[4:8, :]
# or market_df.iloc[4:8, ]
# Selecting a single column
# Notice that the column index starts at 0, and 2 represents the third column (Cust_id)
market_df.iloc[:, 2]
# Selecting multiple columns
market_df.iloc[:, 3:8]
# Selecting multiple rows and columns
market_df.iloc[3:6, 2:5]
# Using booleans
# This selects the rows corresponding to True
market_df.iloc[[True, True, False, True, True, False, True]]
Explanation: Note that simply writing df[2, 4] will throw an error, since pandas gets confused whether the 2 is an integer index (the third row), or is it a row with label = 2? 
On the other hand, df.iloc[2, 4] tells pandas explicitly that it should assume integer indices.
End of explanation
help(pd.DataFrame.loc)
Explanation: To summarise, df.iloc[x, y] uses integer indices starting at 0.
The other common way of indexing is the label based indexing, which uses df.loc[]. 
Label Based Indexing
Pandas provides the df.loc[] functionality to index dataframes using labels.
End of explanation
# Selecting a single element
# Select row label = 2 and column label = 'Sales
market_df.loc[2, 'Sales']
# Selecting a single row using a single label
# df.loc reads 5 as a label, not index
market_df.loc[5]
# or equivalently
market_df.loc[5, :]
# or market_df.loc[5, ]
# Select multiple rows using a list of row labels
market_df.loc[[3, 7, 8]]
# Or equivalently
market_df.loc[[3, 7, 8], :]
# Selecting rows using a range of labels
# Notice that with df.loc, both 4 and 8 are included, unlike with df.iloc
# This is an important difference between iloc and loc
market_df.loc[4:8]
# Or equivalently
market_df.loc[4:8, ]
# Or equivalently
market_df.loc[4:8, :]
# The use of label based indexing will be more clear when we have custom row indices
# Let's change the indices to Ord_id
market_df.set_index('Ord_id', inplace = True)
market_df.head()
# Select Ord_id = Ord_5406 and some columns
market_df.loc['Ord_5406', ['Sales', 'Profit', 'Cust_id']]
# Select multiple orders using labels, and some columns
market_df.loc[['Ord_5406', 'Ord_5446', 'Ord_5485'], 'Sales':'Profit']
# Using booleans
# This selects the rows corresponding to True
market_df.loc[[True, True, False, True, True, False, True]]
Explanation: As mentioned in the documentation, the inputs x, y to df.loc[x, y] can be:
* A single label, e.g. '3' or 'row_index'
* A list or array of labels, e.g. ['3', '7', '8']
* A range of labels, where row_x and row_y both are included, i.e. 'row_x':'row_y'
* A boolean array <br>
Let's see some examples.
End of explanation
<END_TASK>