library(readr)
library(ggplot2)
library(readr)
Machinery_STA4813 <- read_csv("~/Documents/Unisa 2024/STA4813/Assignment 1 - 2024/Machinery_STA4813.csv")
## Rows: 27 Columns: 13
## ── Column specification ────────────────────────────────────────────────────────
## Delimiter: ","
## chr (2): Type_Tractor, Type_Fruit
## dbl (11): Tractor_Power, Average_Purchase_Price, Salvage_Value, Average_Inve...
##
## ℹ Use `spec()` to retrieve the full column specification for this data.
## ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
Machinery_STA4813$Type_Tractor <- as.factor(Machinery_STA4813$Type_Tractor)
Machinery_STA4813$Type_Fruit <- as.factor(Machinery_STA4813$Type_Fruit)
Machinery_STA4813
## # A tibble: 27 × 13
## Tractor_Power Type_Tractor Type_Fruit Average_Purchase_Price Salvage_Value
## <dbl> <fct> <fct> <dbl> <dbl>
## 1 48 2 WD Vineyard 494800 49480
## 2 36 2 WD Orchards 344400 34440
## 3 44 2 WD Orchards 433750 43375
## 4 48 2 WD Orchards 412902 41290
## 5 51 2 WD Orchards 573500 57350
## 6 52 2 WD Orchards 350625 35063
## 7 53 2 WD Orchards 460200 46020
## 8 56 2 WD Orchards 847768 84777
## 9 57 2 WD Orchards 604950 60495
## 10 59 2 WD Orchards 478500 47850
## # ℹ 17 more rows
## # ℹ 8 more variables: Average_Investment <dbl>, Depreciation_Costs <dbl>,
## # Insurance_Licence_Costs <dbl>, Interest_Costs <dbl>,
## # Total_Fixed_Costs <dbl>, Repair_Maintenance_Costs <dbl>, Fuel_Costs <dbl>,
## # Fuel_Usage <dbl>
The dataset “Machinery.csv” has undergone cleaning and pre-processing using SPSS and R. It has now been successfully loaded into R-studio using the provided codes. A cursory examination of the data reveals that there are 27 observations and 13 variables, which will be utilized in later analysis.
Using the following R-codes, we will now examine the dataset more closely, including the characteristics of its variables, to comprehend its nature and derive useful insights from our anticipated data analyses.
head(Machinery_STA4813)
## # A tibble: 6 × 13
## Tractor_Power Type_Tractor Type_Fruit Average_Purchase_Price Salvage_Value
## <dbl> <fct> <fct> <dbl> <dbl>
## 1 48 2 WD Vineyard 494800 49480
## 2 36 2 WD Orchards 344400 34440
## 3 44 2 WD Orchards 433750 43375
## 4 48 2 WD Orchards 412902 41290
## 5 51 2 WD Orchards 573500 57350
## 6 52 2 WD Orchards 350625 35063
## # ℹ 8 more variables: Average_Investment <dbl>, Depreciation_Costs <dbl>,
## # Insurance_Licence_Costs <dbl>, Interest_Costs <dbl>,
## # Total_Fixed_Costs <dbl>, Repair_Maintenance_Costs <dbl>, Fuel_Costs <dbl>,
## # Fuel_Usage <dbl>
str(Machinery_STA4813)
## spc_tbl_ [27 × 13] (S3: spec_tbl_df/tbl_df/tbl/data.frame)
## $ Tractor_Power : num [1:27] 48 36 44 48 51 52 53 56 57 59 ...
## $ Type_Tractor : Factor w/ 2 levels "2 WD","4 WD": 1 1 1 1 1 1 1 1 1 1 ...
## $ Type_Fruit : Factor w/ 2 levels "Orchards","Vineyard": 2 1 1 1 1 1 1 1 1 1 ...
## $ Average_Purchase_Price : num [1:27] 494800 344400 433750 412902 573500 ...
## $ Salvage_Value : num [1:27] 49480 34440 43375 41290 57350 ...
## $ Average_Investment : num [1:27] 222660 154980 195188 185806 258075 ...
## $ Depreciation_Costs : num [1:27] 44.5 31 39 37.2 51.6 ...
## $ Insurance_Licence_Costs : num [1:27] 2.23 1.55 1.95 1.86 2.58 1.58 2.07 3.81 2.72 2.15 ...
## $ Interest_Costs : num [1:27] 28.9 20.1 25.4 24.1 33.5 ...
## $ Total_Fixed_Costs : num [1:27] 46.8 32.5 41 39 54.2 ...
## $ Repair_Maintenance_Costs: num [1:27] 59.4 41.3 52 49.5 68.8 ...
## $ Fuel_Costs : num [1:27] 182 136 166 182 193 ...
## $ Fuel_Usage : num [1:27] 8.64 6.48 7.92 8.64 9.18 ...
## - attr(*, "spec")=
## .. cols(
## .. Tractor_Power = col_double(),
## .. Type_Tractor = col_character(),
## .. Type_Fruit = col_character(),
## .. Average_Purchase_Price = col_double(),
## .. Salvage_Value = col_double(),
## .. Average_Investment = col_double(),
## .. Depreciation_Costs = col_double(),
## .. Insurance_Licence_Costs = col_double(),
## .. Interest_Costs = col_double(),
## .. Total_Fixed_Costs = col_double(),
## .. Repair_Maintenance_Costs = col_double(),
## .. Fuel_Costs = col_double(),
## .. Fuel_Usage = col_double()
## .. )
## - attr(*, "problems")=<externalptr>
The “head” command comfortably offers us a preview of the entire data. The variables in this dataset (in order) are: Tractor Power in Kilowatts (kW), Type of Tractor (2-Wheel Drive Tractor or 4-Wheel Drive Tractor), Type of Fruit (Vineyard or Orchards), Average Purchase Price in South African Rand (R), Salvage Value in South African Rand, Average investment in South African Rand, Depreciation costs per hour (in R/h), Insurance and licence costs per hour (in R/h), Interest cost per hour (in R/h), Total fixed costs excluding interest, Repair & Maintenance costs per hour (in R/h), and Fuel costs (in R/h).
The “str” command is another useful way to examine the dataset as an R object. We can clearly see that 2 of the 13 variables are categorical variables and are therefore “Factor Variables”. These 2 are: “Type of Tractor (2-Wheel Drive Tractor or 4-Wheel Drive Tractor)” and “Type of Fruit (Vineyard or Orchards)”.
The remaining 11 variables are quantivative. Of these quantitative variables, “Tractor Power in Kilowatts (kW)”, “Average Purchase Price in South African Rand (R)”, “Salvage Value in South African Rand”, and “Average investment in South African Rand” are integers, while “Depreciation costs per hour (in R/h)”, “Insurance and licence costs per hour (in R/h)”, “Interest cost per hour (in R/h)”, “Total fixed costs excluding interest”, “Repair & Maintenance costs per hour (in R/h)”, and “Fuel costs (in R/h)” are interval or continuous variables.
summary(Machinery_STA4813)
## Tractor_Power Type_Tractor Type_Fruit Average_Purchase_Price
## Min. :36.00 2 WD:11 Orchards:25 Min. : 266650
## 1st Qu.:48.00 4 WD:16 Vineyard: 2 1st Qu.: 446975
## Median :53.00 Median : 526400
## Mean :53.78 Mean : 566553
## 3rd Qu.:59.00 3rd Qu.: 631840
## Max. :71.00 Max. :1171456
## Salvage_Value Average_Investment Depreciation_Costs Insurance_Licence_Costs
## Min. : 26665 Min. :119993 Min. : 24.00 Min. :1.200
## 1st Qu.: 44698 1st Qu.:201139 1st Qu.: 40.23 1st Qu.:2.010
## Median : 52640 Median :236880 Median : 47.38 Median :2.370
## Mean : 56655 Mean :254949 Mean : 50.99 Mean :2.549
## 3rd Qu.: 63184 3rd Qu.:284328 3rd Qu.: 56.87 3rd Qu.:2.840
## Max. :117146 Max. :527155 Max. :105.43 Max. :5.270
## Interest_Costs Total_Fixed_Costs Repair_Maintenance_Costs Fuel_Costs
## Min. :15.60 Min. : 25.20 Min. : 32.00 Min. :136.1
## 1st Qu.:26.14 1st Qu.: 42.24 1st Qu.: 53.63 1st Qu.:181.5
## Median :30.79 Median : 49.74 Median : 63.17 Median :200.4
## Mean :33.14 Mean : 53.54 Mean : 67.99 Mean :203.4
## 3rd Qu.:36.96 3rd Qu.: 59.70 3rd Qu.: 75.82 3rd Qu.:223.1
## Max. :68.53 Max. :110.70 Max. :140.57 Max. :268.5
## Fuel_Usage
## Min. : 6.480
## 1st Qu.: 8.640
## Median : 9.540
## Mean : 9.733
## 3rd Qu.:10.800
## Max. :12.780
The output above provides a basic numerical representation of our data. For both categorical variables, we obtain the number of observations and the corresponding class for each factor.
For the numerical variables, we have eleven summary statistics that provide a rough understanding of the distributions.
Finding a linear model to predict tractor average purchase price is our next step.
Question 1(a): Construct appropriate graphs and calculate appropriate summary statistics of both Average_Purchase_Price and Tractor_Power individually and then together. What is your conclusion?
Step 1: Generate graphs for Average_Purchase_Price individually
library(ggplot2)
library(patchwork)
# Create histogram
histogram <- ggplot(Machinery_STA4813, aes(x = Average_Purchase_Price)) +
geom_histogram(binwidth = 100000, fill = "lightblue", color = "black") +
labs(title = "Distribution of Average Purchase Price",
x = "Average Purchase Price",
y = "Frequency")
# Create boxplot
boxplot <- ggplot(Machinery_STA4813, aes(x = "", y = Average_Purchase_Price)) +
geom_boxplot(fill = "lightblue", color = "black") +
labs(title = "Boxplot of Average Purchase Price",
x = "",
y = "Average Purchase Price")
# Create kernel density plot
plot(density(Machinery_STA4813$Average_Purchase_Price),main="Average_Purchase_Price")
rug(Machinery_STA4813$Average_Purchase_Price)
# Arrange the plots side by side
(histogram + boxplot)
summary(Machinery_STA4813$Average_Purchase_Price)
## Min. 1st Qu. Median Mean 3rd Qu. Max.
## 266650 446975 526400 566553 631840 1171456
The observed range of average purchase prices is from R266,650 to R1,171,456, with a mean price of R566,553.
It is clear by looking at the histogram and, more specifically, the kernel density plot, that the distribution is right-skewed, (since the mean value is greater than the median value), and that there are two large outliers in the right tail. It is highly doubtful therefore, that this distribution follows a normal assumption. The appearance of two separate values in the boxplot helps to further clarify the outliers.
# Confirming the presence of outlier(s)
# Identify potential outliers
outliers <- boxplot(Machinery_STA4813$Average_Purchase_Price)$out
# Print the identified outliers
print(outliers)
## [1] 911397 1171456
The R-codes provided us with outputs that allowed us to more precisely identify the outliers described earlier. These outliers are the “Average Purchase Prices” with values of R911,379 and R1,171,456. Currently, it is uncertain if these outliers are influential points that need to be eliminated or if they demand a transformation of our variable. This will be determined as our analyses go.
Step 2: Generate graphs for Tractor_Power individually
library(ggplot2)
library(patchwork)
# Create histogram
histogram <- ggplot(Machinery_STA4813, aes(x = Tractor_Power)) +
geom_histogram(binwidth = 5, fill = "lightblue", color = "black") +
labs(title = "Distribution of Tractor_Power",
x = "Tractor_Power",
y = "Frequency")
# Create boxplot
boxplot <- ggplot(Machinery_STA4813, aes(x = "", y = Tractor_Power)) +
geom_boxplot(fill = "lightblue", color = "black") +
labs(title = "Boxplot of Tractor_Power",
x = "",
y = "Tractor_Power")
# Create kernel density plot
plot(density(Machinery_STA4813$Tractor_Power),main="Tractor_Power")
rug(Machinery_STA4813$Tractor_Power)
# Arrange the plots side by side
(histogram + boxplot)
summary(Machinery_STA4813$Tractor_Power)
## Min. 1st Qu. Median Mean 3rd Qu. Max.
## 36.00 48.00 53.00 53.78 59.00 71.00
According to the output above, the minimum tractor power is 36.00 kilowatts, and the highest is 71.00 kilowatts. The average tractor power is 53.78 kilowatts. The kernel density figure shows that the data is approximately symmetrically (or uniformly) distributed, with the majority of it centered around the mean. The histogram shows no substantial skewness. The boxplot is also positioned centrally in the data, indicating the absence of outliers.
Step 3: Any meaningful relationships between Average purchase price & tractor power?
# Generate a scatter plot for Average_Purchase_Price and Tractor_Power together
ggplot(Machinery_STA4813, aes(x = Tractor_Power, y = Average_Purchase_Price)) +
geom_point(color = "blue") +
labs(title = "Scatter Plot of Average_Purchase_Price vs. Tractor_Power",
x = "Tractor Power",
y = "Average Purchase Price")
# Calculate correlation coefficient
round(cor(Machinery_STA4813$Tractor_Power, Machinery_STA4813$Average_Purchase_Price), 3)
## [1] 0.606
A visual representation of the relationship between the two variables is depicted above according to the scatter plot. The data points exhibit an upward trend which signifies a positive correlation.This means that higher-powered tractors tend to be purchased for a greater average price.
The correlation coefficient of 0.606 suggests that Average Purchase Price and Tractor Power are correlated in a moderately positive manner, even though the relationship is not a perfectly positive one.
We should bear in mind however, that correlation does not necessarily indicate causation; i.e. although a positive correlation exists between tractor power and average purchase price, there may be additional determinants of average purchase price that are not accounted for in this analysis.
Question 1(b): Fit a simple linear regression model with Average_Purchase_Price as the response variable and Tractor_Power as the explanatory variable (Model 1). Interpret the estimate slope coefficient β1. Are all assumptions of the linear regression of the met by the data?
# Fitting the linear regression model
model1 <- lm(Average_Purchase_Price ~ Tractor_Power, data = Machinery_STA4813)
# Printing the model summary
model1sum <- summary(model1)
model1sum
##
## Call:
## lm(formula = Average_Purchase_Price ~ Tractor_Power, data = Machinery_STA4813)
##
## Residuals:
## Min 1Q Median 3Q Max
## -360398 -104736 7289 49869 429788
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) -203953 204543 -0.997 0.328262
## Tractor_Power 14328 3760 3.811 0.000804 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 161100 on 25 degrees of freedom
## Multiple R-squared: 0.3675, Adjusted R-squared: 0.3422
## F-statistic: 14.52 on 1 and 25 DF, p-value: 0.0008037
# Printing the coefficients of model1
coef(model1)
## (Intercept) Tractor_Power
## -203952.56 14327.59
The summary of the linear regression model (model1) is provided above.
Interpretation of the slope coefficient[Tractor_Power (β1)]: The predicted slope coefficient of 14328 represents the expected rise in the average purchase price for each unit of tractor power. In this scenario, as tractor power increases by one unit, the average purchase price is predicted to rise by about R14328, while other factors remain constant. The p-value of 0.000804 indicates that the slope coefficient is statistically significant at 0.05 alpha level.
model1sum$r.squared
## [1] 0.3674703
The coefficient of determination (R-squared) is 0.3675, indicating that 36.75% of the variability in the model can be explained by the Tractor power variable. Given the relatively low R-squared value, it suggests that the model may not comprehensively incorporate all the factors that contribute to the variability in the response variable. The comparatively low R-squared score suggests that there is room for improvement in the model.
deviance(model1)
## [1] 648985891470
To further assess the goodness of fit of the regression model1, we have provided the deivance; a measure of the discrepancy between the observed data and the model’s predicted values. The deviance above seems too large for a good model.
Since the intercept (β0) = -203953; a result which has no contextual meaning when estimating the Average Purchase Price of a tractor, we may want to consider the following improvement analysis:
Machinery_STA4813$Average_Purchase_Price_Centering <- Machinery_STA4813$Average_Purchase_Price - mean( Machinery_STA4813$Average_Purchase_Price)
Machinery_STA4813$Tractor_Power_Centering <- Machinery_STA4813$Tractor_Power - mean(Machinery_STA4813$Tractor_Power)
Model_1_centering <- lm(Average_Purchase_Price_Centering ~ Tractor_Power_Centering, Machinery_STA4813)
summary(Model_1_centering)
##
## Call:
## lm(formula = Average_Purchase_Price_Centering ~ Tractor_Power_Centering,
## data = Machinery_STA4813)
##
## Residuals:
## Min 1Q Median 3Q Max
## -360398 -104736 7289 49869 429788
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) -3.991e-11 3.101e+04 0.000 1.000000
## Tractor_Power_Centering 1.433e+04 3.760e+03 3.811 0.000804 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 161100 on 25 degrees of freedom
## Multiple R-squared: 0.3675, Adjusted R-squared: 0.3422
## F-statistic: 14.52 on 1 and 25 DF, p-value: 0.0008037
coef(summary(Model_1_centering))
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) -3.991025e-11 31007.43 -1.287119e-15 1.000000000
## Tractor_Power_Centering 1.432759e+04 3759.52 3.811015e+00 0.000803672
By centering the mean as observed previously, the updated intercept (β0) is now -3.991025e-11 (approximately zero), which provides a more significant interpretation to the Average Purchase Price when the tractor power remains constant (or zero), specifically R0.00 South African Rands will be expended when the Tractor Power is also zero kilowatts. Nevertheless, the remaining parameters (“Multiple R-squared”, “β1”, and standard error) of this model remain unchanged. Therefore, we would pursue additional enhancements for this model.
deviance(Model_1_centering)
## [1] 648985891470
Deviance still remain unchanged also.
# Diagnostic plots.
# Set the layout to have two rows and two columns
par(mfrow = c(2, 2))
# Scatter plot of residuals vs. fitted values
plot(model1, which = 1)
# Scatter plot of square-root of standardized residuals vs. fitted values
plot(model1, which = 3)
# Histogram of residuals
plot(model1, which = 2)
# Plot of standardized residuals vs leverage
plot(model1, which = 5)
# Reset the layout back to the default
par(mfrow = c(1, 1))
# Calculating Cook's distance
cooksd <- cooks.distance(model1)
# Identifying influential points
influential_points <- which(cooksd > 4 / length(cooksd))
# Printing the influential points
print(influential_points)
## 26
## 26
The first plot displays the residuals plotted against the fitted values. This plot can be utilized to identify the presence of lack of fit and to evaluate the assumption of constant variance. Firstly, there are outliers identified and one of them is even an influential point. The curve has a subtle curved pattern or divergence from the dotted line, as the red line is consistently below the zero line and the residuals tend to be negative. This indicates that the model tends to underestimate the response variable, suggesting that a modification to the model may be necessary, such as transforming one of the variables. The residuals do not appear to have a constant variance.
The next diagnostic tool to explore is the normal quantile-quantile (Q-Q) plot. In this instance, the figure demonstrates that the data distribution closely aligns with the dotted lines, except for the presence of outliers or influential points. The assumption of normality is consequently broken (or violated) as well.
Analyzing the spread and dispersion of data points allows for an interpretation of the scale-location plot that is comparable to that of the residual versus fitted plot. When we look at the spread from left to right in the plot above, we see a funnel shape or a somewhat different spread and pattern, which suggests heteroscedasticity (i.e. non-constant variance). Significant deviations from the general pattern, or outlying points, also signal to important findings or possible problems with the model. In conclusion, there is a breach of the constant variance assumption.
The residual versus leverage plot clearly indicates the presence of an influential observation, suggesting that the model should be modified or a variable should be transformed.
To summarize, despite a modest level of linearity (correlation = 0.606) between the average purchase price and tractor power, the criteria of normality and homoscedasticity are violated. As a result, not all requirements for linear regression are met by the data.
Question 1(c):Create a new variable logAverage_Purchase_Price, the natural log of Average_Purchase_Price. Fit Model 2 where logAverage_Purchase_Price is now the response variable and Tractor_Power is still the explanatory variable. Write down the estimated regression line equation.
# Create the new variable logAverage_Purchase_Price
Machinery_STA4813$logAverage_Purchase_Price <- log(Machinery_STA4813$Average_Purchase_Price)
# Fit Model 2 with logAverage_Purchase_Price as the response variable and Tractor_Power as the explanatory variable
model2 <- lm(logAverage_Purchase_Price ~ Tractor_Power, data = Machinery_STA4813)
# Print the estimated regression line equation
summary(model2)
##
## Call:
## lm(formula = logAverage_Purchase_Price ~ Tractor_Power, data = Machinery_STA4813)
##
## Residuals:
## Min 1Q Median 3Q Max
## -0.80020 -0.13471 0.01824 0.12945 0.49020
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) 11.918847 0.339158 35.142 < 2e-16 ***
## Tractor_Power 0.023708 0.006234 3.803 0.00082 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 0.2672 on 25 degrees of freedom
## Multiple R-squared: 0.3665, Adjusted R-squared: 0.3412
## F-statistic: 14.46 on 1 and 25 DF, p-value: 0.00082
coef(model2)
## (Intercept) Tractor_Power
## 11.91884732 0.02370773
logAverage_Purchase_Price = 11.918847 + 0.023708 * Tractor_Power
In the equation above, the intercept (estimated coefficient for the (Intercept) term) is 11.918847, and the slope (estimated coefficient for the Tractor_Power term) is 0.023708.
deviance(model2)
## [1] 1.784321
Question 1(d): How does logAverage_Purchase_Price change when Tractor_Power increases by 1?
The coefficient indicates that for every one-unit rise in the Tractor_Power, the logAverage_Purchase_Price is predicted to increase by about 0.023708.
Question 1(e): Recall that log(a) −log(b) = log( a/b). Use this to explain/find out how Average_Purchase_Price changes as Tractor_Power increases by 1.
Since logAverage_Purchase_Price = 11.918847 + 0.023708 * Tractor_Power, then as tractor power increase by 1, it implies: log(Average_Purchase_Price_new) = 11.918847 + 0.023708 * 1 = 11.94255. Hence,
Average_Purchase_Price_new <- exp(11.94255)
Average_Purchase_Price_new
## [1] 153668
Therefore average power changes by 153668 units.
Question 1(f): Are linear least squares regression (LLSR) assumptions satisfied in Model 2? Why or why not?
Just as we diagnosed for model1
# Diagnostic plots.
# Set the layout to have two rows and two columns
par(mfrow = c(2, 2))
# Scatter plot of residuals vs. fitted values
plot(model2, which = 1)
# Scatter plot of square-root of standardized residuals vs. fitted values
plot(model2, which = 3)
# Histogram of residuals
plot(model2, which = 2)
# Plot of standardized residuals vs leverage
plot(model2, which = 5)
# Reset the layout back to the default
par(mfrow = c(1, 1))
Again,
The first plot displays the residuals plotted against the fitted values. The curve has a no divergence from the dotted line this time, as the red line is consistently along line and the residuals randomly distributed. This indicates that the model tends to represented the response variable. There might be a worrying outlier identified as 21. The residuals appear to have a constant variance.
The normal quantile-quantile (Q-Q) plot in this case, demonstrates that the data distribution closely aligns with the dotted lines. However, some slight cyclic patterns are observed. The data appears normally distributed.
The scale-location plot looks at the spread from left to right, and we see a more even spread, which suggests homoscedasticity (constant variance). However, there might be a prominent outlier which in conclusion, shows a breach of the constant variance assumption.
The residual versus leverage plot indicates the absence of an influential observation, suggesting that the model satisfies normality.
To summarize, the criterion of normality is satisfied, but that of homoscedasticity seems violated. As a result, not all requirements for linear regression are met by the data.
_** Question 1(g):Fit Model 3 with Average_Purchase_Price as the response and Tractor_Power and Type_Tractor as predictors or explanatory variables. Write down the estimated regression line equation and interpret all the regression coefficients in the fitted model**_
# Convert 2WD to 0 and 4WD to 1
Machinery_STA4813$Type_Tractor <- as.numeric(Machinery_STA4813$Type_Tractor) - 1
Machinery_STA4813$Type_Tractor
## [1] 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
model_3 <- lm(Average_Purchase_Price ~ Tractor_Power + Type_Tractor, data = Machinery_STA4813)
summary(model_3)
##
## Call:
## lm(formula = Average_Purchase_Price ~ Tractor_Power + Type_Tractor,
## data = Machinery_STA4813)
##
## Residuals:
## Min 1Q Median 3Q Max
## -373071 -110850 22677 38741 421535
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) -196061 207907 -0.943 0.35507
## Tractor_Power 13775 3939 3.497 0.00186 **
## Type_Tractor 36836 66127 0.557 0.58265
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 163400 on 24 degrees of freedom
## Multiple R-squared: 0.3755, Adjusted R-squared: 0.3235
## F-statistic: 7.217 on 2 and 24 DF, p-value: 0.003516
coef(model_3)
## (Intercept) Tractor_Power Type_Tractor
## -196060.95 13774.94 36835.91
# Extract the coefficients and their variable names
coefficients <- coef(model_3)
variable_names <- names(coefficients)
# Create the MLR equation string
mlr_equation <- paste("Average_Purchase_Price =", coefficients[1], "+", paste(coefficients[-1], variable_names[-1], collapse = " + "))
# Print the MLR equation
cat("MLR Equation:", mlr_equation)
## MLR Equation: Average_Purchase_Price = -196060.954444562 + 13774.9388278195 Tractor_Power + 36835.9120005814 Type_Tractor
model_3sum<-summary(model_3)
model_3sum$r.squared
## [1] 0.3755442
The intercept term (β0 = -159225.04) indicates the projected average purchase price for a tractor that has no Tractor_Power and is of Type_Tractor 2WD. Nevertheless, due to the fact that 2WD is not a numerical variable, we approach the interpretation of this coefficient with care and place greater emphasis on the other predictors.
The coefficient Tractor_Power (β1 = 13774.94) represents the expected rise in the average purchase price for each incremental unit of Tractor_Power, assuming that the Type_Tractor remains unchanged. Hence, a one-unit increment in Tractor_Power is projected to result in an average purchase price increase of around R13,774.94.
Type_Tractor (β2 = 36835.91): This coefficient quantifies the expected variation in the mean buying cost between Type_Tractor 4WD and Type_Tractor 2WD, while keeping Tractor_Power constant. On average, Type_Tractor 4WD tractors are anticipated to have a higher mean purchase price than Type_Tractor 2WD tractors by roughly R36,835.91.
_** Question 1(h): Are LLSR assumptions satisfied in Model 3? Why or why not?**_
# Diagnostic plots.
# Set the layout to have two rows and two columns
par(mfrow = c(2, 2))
# Scatter plot of residuals vs. fitted values
plot(model_3, which = 1)
# Scatter plot of square-root of standardized residuals vs. fitted values
plot(model_3, which = 3)
# Histogram of residuals
plot(model_3, which = 2)
# Plot of standardized residuals vs leverage
plot(model_3, which = 5)
# Reset the layout back to the default
par(mfrow = c(1, 1))
_** Question 1(i): Calculate the correlation matrix of Average_Purchase_Price, Fuel_Usage, Salvage_Value, Average_Investment, Depreciation_Costs, Insurance_Licence_Costs, Interest_Costs and Repair_Maintenance_Costs. What do you observe in the correlation matrix? Do you recommend any explanatory variable from these variables (from Fuel_Usage, Salvage_Value, Average_Investment, Depreciation_Costs, Insurance_Licence_Costs, Interest_Costs and Repair_Maintenance_Costs) to be added to Model 3 to create a model with a higher adjusted R2 value? Why? Explain the reason from LLSR assumptions point of view**_
correlation_matrix <- cor(Machinery_STA4813[c("Average_Purchase_Price", "Fuel_Usage", "Salvage_Value", "Average_Investment", "Depreciation_Costs", "Insurance_Licence_Costs", "Interest_Costs", "Repair_Maintenance_Costs")])
correlation_matrix
## Average_Purchase_Price Fuel_Usage Salvage_Value
## Average_Purchase_Price 1.0000000 0.6524046 1.0000000
## Fuel_Usage 0.6524046 1.0000000 0.6524043
## Salvage_Value 1.0000000 0.6524043 1.0000000
## Average_Investment 1.0000000 0.6524046 1.0000000
## Depreciation_Costs 1.0000000 0.6524095 1.0000000
## Insurance_Licence_Costs 0.9999970 0.6517110 0.9999970
## Interest_Costs 1.0000000 0.6523766 1.0000000
## Repair_Maintenance_Costs 1.0000000 0.6524099 1.0000000
## Average_Investment Depreciation_Costs
## Average_Purchase_Price 1.0000000 1.0000000
## Fuel_Usage 0.6524046 0.6524095
## Salvage_Value 1.0000000 1.0000000
## Average_Investment 1.0000000 1.0000000
## Depreciation_Costs 1.0000000 1.0000000
## Insurance_Licence_Costs 0.9999970 0.9999969
## Interest_Costs 1.0000000 1.0000000
## Repair_Maintenance_Costs 1.0000000 1.0000000
## Insurance_Licence_Costs Interest_Costs
## Average_Purchase_Price 0.9999970 1.0000000
## Fuel_Usage 0.6517110 0.6523766
## Salvage_Value 0.9999970 1.0000000
## Average_Investment 0.9999970 1.0000000
## Depreciation_Costs 0.9999969 1.0000000
## Insurance_Licence_Costs 1.0000000 0.9999971
## Interest_Costs 0.9999971 1.0000000
## Repair_Maintenance_Costs 0.9999971 1.0000000
## Repair_Maintenance_Costs
## Average_Purchase_Price 1.0000000
## Fuel_Usage 0.6524099
## Salvage_Value 1.0000000
## Average_Investment 1.0000000
## Depreciation_Costs 1.0000000
## Insurance_Licence_Costs 0.9999971
## Interest_Costs 1.0000000
## Repair_Maintenance_Costs 1.0000000
# Calculate the absolute correlation values
abs_correlation <- abs(correlation_matrix[, "Average_Purchase_Price"])
# Find the variable with the least correlation
variable_least_correlation <- names(abs_correlation)[which.min(abs_correlation)]
# Print the variable with the least correlation
cat("Variable with the least correlation:", variable_least_correlation)
## Variable with the least correlation: Fuel_Usage
Fuel_Usage has the least correlation and can be added to model_3. Almost every variable risk multicollinearity because of their very high or perfect correlation with one another. Hence,
model_3_new <- lm(Average_Purchase_Price ~ Tractor_Power + Type_Tractor + Fuel_Usage, data = Machinery_STA4813)
summary(model_3_new)
##
## Call:
## lm(formula = Average_Purchase_Price ~ Tractor_Power + Type_Tractor +
## Fuel_Usage, data = Machinery_STA4813)
##
## Residuals:
## Min 1Q Median 3Q Max
## -351183 -88435 17233 54730 451015
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) -175796 180511 -0.974 0.34025
## Tractor_Power -65239 26730 -2.441 0.02278 *
## Type_Tractor 49718 57535 0.864 0.39643
## Fuel_Usage 433696 145515 2.980 0.00669 **
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 141800 on 23 degrees of freedom
## Multiple R-squared: 0.5495, Adjusted R-squared: 0.4908
## F-statistic: 9.352 on 3 and 23 DF, p-value: 0.0003143
model_3_newsum<-summary(model_3_new)
model_3_newsum$adj.r.squared
## [1] 0.4907664
There is a rise in the new adjusted R-squared value after adding fuel usage.
# Diagnostic plots.
# Set the layout to have two rows and two columns
par(mfrow = c(2, 2))
# Scatter plot of residuals vs. fitted values
plot(model_3_new, which = 1)
# Scatter plot of square-root of standardized residuals vs. fitted values
plot(model_3_new, which = 3)
# Histogram of residuals
plot(model_3_new, which = 2)
# Plot of standardized residuals vs leverage
plot(model_3_new, which = 5)
# Reset the layout back to the default
par(mfrow = c(1, 1))
The LLSR assumptions are still not met primarily because of the presence of the outliers or influential point.
We will now check for the outlier and remove it.
# Assuming you have previously fitted the regression model "model_3_new"
# Calculating Cook's distance
cooksd <- cooks.distance(model_3_new)
# Identifying influential points
influential_points <- which(cooksd > 4 / length(cooksd))
# Identifying outliers (including influential points)
outliers <- which(cooksd > 4 / length(cooksd))
# Printing the influential points
print(influential_points)
## 26
## 26
# Printing the outliers
print(outliers)
## 26
## 26
# Assuming the outlier(s) or influential observation(s) are identified and stored in the "influential_points" variable
# Create a new dataset without the outlier(s)
Machinery_STA4813_New <- Machinery_STA4813[!rownames(Machinery_STA4813) %in% influential_points, ]
# Re-fit the regression model with the new dataset
model4 <- lm(Average_Purchase_Price ~ Tractor_Power + Type_Tractor + Fuel_Usage, data = Machinery_STA4813_New)
# Print the summary of the new model
summary(model4)
##
## Call:
## lm(formula = Average_Purchase_Price ~ Tractor_Power + Type_Tractor +
## Fuel_Usage, data = Machinery_STA4813_New)
##
## Residuals:
## Min 1Q Median 3Q Max
## -308927 -35590 2832 54140 143448
##
## Coefficients:
## Estimate Std. Error t value Pr(>|t|)
## (Intercept) -11540 134156 -0.086 0.932232
## Tractor_Power -75185 19310 -3.894 0.000781 ***
## Type_Tractor 31767 41490 0.766 0.452012
## Fuel_Usage 470888 104790 4.494 0.000181 ***
## ---
## Signif. codes: 0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
##
## Residual standard error: 101800 on 22 degrees of freedom
## Multiple R-squared: 0.6471, Adjusted R-squared: 0.599
## F-statistic: 13.45 on 3 and 22 DF, p-value: 3.364e-05
model4sum<-summary(model4)
model4sum$adj.r.squared
## [1] 0.5989653
The model now looks better with an improved Adjusted R-squared value of approximately 60%.
# Diagnostic plots.
# Set the layout to have two rows and two columns
par(mfrow = c(2, 2))
# Scatter plot of residuals vs. fitted values
plot(model4, which = 1)
# Scatter plot of square-root of standardized residuals vs. fitted values
plot(model4, which = 3)
# Histogram of residuals
plot(model4, which = 2)
# Plot of standardized residuals vs leverage
plot(model4, which = 5)
# Reset the layout back to the default
par(mfrow = c(1, 1))
The LLSR assumptions are now fulfilled as seen from the four diagnostic plots above; Linearity, Normality, Homoscedasticity and independence of errors are all valid.