Skip to content

Commit 4e795e9

Browse files
display both types of dof (#231)
* display both types of df * Update README.md * Update Project.toml * Update README.md * Update README.md
1 parent ba6228e commit 4e795e9

File tree

4 files changed

+26
-26
lines changed

4 files changed

+26
-26
lines changed

Project.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
name = "FixedEffectModels"
22
uuid = "9d5cd8c9-2029-5cab-9928-427838db53e3"
3-
version = "1.9.1"
3+
version = "1.9.2"
44

55
[deps]
66
DataFrames = "a93c6f00-e57d-5684-b7b6-d8193f3e46c0"

README.md

Lines changed: 12 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -17,17 +17,18 @@ The objective of the package is similar to the Stata command [`reghdfe`](https:/
1717
using DataFrames, RDatasets, FixedEffectModels
1818
df = dataset("plm", "Cigar")
1919
reg(df, @formula(Sales ~ NDI + fe(State) + fe(Year)), Vcov.cluster(:State), weights = :Pop)
20-
# =====================================================================
21-
# Number of obs: 1380 Degrees of freedom: 32
22-
# R2: 0.803 R2 Adjusted: 0.798
23-
# F Statistic: 13.3382 p-value: 0.001
24-
# R2 within: 0.139 Iterations: 6
25-
# Converged: true
26-
# =====================================================================
27-
# Estimate Std.Error t value Pr(>|t|) Lower 95% Upper 95%
28-
# ---------------------------------------------------------------------
29-
# NDI -0.00526264 0.00144097 -3.65216 0.000 -0.00808942 -0.00243586
30-
# =====================================================================
20+
FixedEffectModel
21+
=========================================================================
22+
Number of obs: 1380 Converged: true
23+
dof (model): 1 dof (residuals): 45
24+
R²: 0.803 R² adjusted: 0.798
25+
F-statistic: 13.3382 P-value: 0.001
26+
R² within: 0.139 Iterations: 5
27+
=========================================================================
28+
Estimate Std. Error t-stat Pr(>|t|) Lower 95% Upper 95%
29+
─────────────────────────────────────────────────────────────────────────
30+
NDI -0.00526264 0.00144097 -3.65216 0.0007 -0.0081649 -0.00236038
31+
=========================================================================
3132
```
3233

3334

src/FixedEffectModel.jl

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,8 @@ struct FixedEffectModel <: RegressionModel
2424
contrasts::Dict
2525

2626
nobs::Int64 # Number of observations
27-
dof::Int64 # Number parameters estimated - has_intercept
28-
dof_residual::Int64 # dof used for t-test and F-stat. nobs - degrees of freedoms with simple std
29-
27+
dof::Int64 # Number parameters estimated - has_intercept. Used for p-value of F-stat.
28+
dof_residual::Int64 # dof used for t-test and p-value of F-stat. nobs - degrees of freedoms with simple std
3029
rss::Float64 # Sum of squared residuals
3130
tss::Float64 # Total sum of squares
3231
r2::Float64 # R squared
@@ -36,8 +35,8 @@ struct FixedEffectModel <: RegressionModel
3635
p::Float64 # p value for the F statistics
3736

3837
# for FE
39-
iterations::Union{Int, Nothing} # Number of iterations
40-
converged::Union{Bool, Nothing} # Has the demeaning algorithm converged?
38+
iterations::Int # Number of iterations
39+
converged::Bool # Has the demeaning algorithm converged?
4140
r2_within::Union{Float64, Nothing} # within r2 (with fixed effect
4241

4342
# for IV
@@ -178,7 +177,9 @@ end
178177
function top(m::FixedEffectModel)
179178
out = [
180179
"Number of obs" sprint(show, nobs(m), context = :compact => true);
181-
"Degrees of freedom" sprint(show, dof(m), context = :compact => true);
180+
"Converged" m.converged;
181+
"dof (model)" sprint(show, dof(m), context = :compact => true);
182+
"dof (residuals)" sprint(show, dof_residual(m), context = :compact => true);
182183
"" @sprintf("%.3f",r2(m));
183184
"R² adjusted" @sprintf("%.3f",adjr2(m));
184185
"F-statistic" sprint(show, m.F, context = :compact => true);

src/fit.jl

Lines changed: 6 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -236,8 +236,8 @@ function StatsAPI.fit(::Type{FixedEffectModel},
236236

237237
# compute tss now before potentially demeaning y
238238
tss_total = tss(y, has_intercept | has_fe_intercept, weights)
239-
# create unitilaized
240-
iterations, converged, r2_within = nothing, nothing, nothing
239+
# initalize fields
240+
iterations, converged, r2_within = 0, true, nothing
241241
F_kp, p_kp = nothing, nothing
242242
collinear_fe = falses(length(var_names_all))
243243

@@ -441,22 +441,20 @@ function StatsAPI.fit(::Type{FixedEffectModel},
441441
end
442442
end
443443
end
444-
dof_residual_ = max(1, nobs - size(X, 2) - dof_fes - dof_add)
445-
dof_ = max(1, size(X, 2) - (has_intercept | has_fe_intercept))
446-
447444

448445
nclusters = nothing
449446
if vcov isa Vcov.ClusterCovariance
450447
nclusters = Vcov.nclusters(vcov_method)
451448
end
452449

453-
454450
# Compute standard error
455-
vcov_data = Vcov.VcovData(Xhat, crossx, residuals, dof_residual_)
451+
vcov_data = Vcov.VcovData(Xhat, crossx, residuals, nobs - size(X, 2) - dof_fes - dof_add)
456452
matrix_vcov = StatsAPI.vcov(vcov_data, vcov_method)
457453

458454
# Compute Fstat
459455
F = Fstat(coef, matrix_vcov, has_intercept)
456+
# dof_ is the number of estimated coefficients beyond the intercept.
457+
dof_ = size(X, 2) - has_intercept
460458
dof_tstat_ = max(1, Vcov.dof_residual(vcov_data, vcov_method) - has_intercept | has_fe_intercept)
461459
p = fdistccdf(dof_, dof_tstat_, F)
462460
# Compute Fstat of First Stage
@@ -477,7 +475,7 @@ function StatsAPI.fit(::Type{FixedEffectModel},
477475
rss = sum(abs2, residuals)
478476
mss = tss_total - rss
479477
r2 = 1 - rss / tss_total
480-
adjr2 = 1 - rss / tss_total * (nobs - (has_intercept | has_fe_intercept)) / dof_residual_
478+
adjr2 = 1 - rss / tss_total * (nobs - (has_intercept | has_fe_intercept)) / max(nobs - size(X, 2) - dof_fes - dof_add, 1)
481479
if has_fes
482480
r2_within = 1 - rss / tss_partial
483481
end

0 commit comments

Comments
 (0)