I dunno about that article. Here's another analysis that shows pretty much the same thing when the Pats return kickoffs -- and those balls are pumped to the max for the kickers. The Pats fumble less than any other team because Belichick benches any back who fumbles the ball and keeps them on the bench sometimes throughout the rest of the season. He also makes them practise with wet and greasy balls all the time. Sounds like "coaching" to me. As far as Patriots hate, that's been around for many years dating even before Spygate -- for two reasons, Belichick's hard to like if you're not a Patriots fan, and some people imvariably just hate winners and success.
"I found this website for data for play by play and the NFL.
Advanced Football Analytics (formerly Advanced NFL Stats): Play-by-Play Data
i downloaded the 2007 - mid 2013 datasets, and analyzed them for kickoff returns/punts.
I found 816 New England return plays that weren't touchbacks or fair catches. I found 10 fumbles on those plays. That's 81 return plays per fumble (error on order +/- 3 fumbles.. so lower bound 62 plays).
I found 24939 non-New England return plays that weren't touchbacks or fair catches, of those 427 resulted in fumbles. That's a rate of 58 return plays per fumble.
So in summary, the Patriots also fumble less on return plays than the league average, though the difference is probably close to the edge of statistical significance.. the measured effect size is about the same.
Given that the balls are over-inflated for kickoffs and not controlled by the patriots, it is impossible for this lower rate of fumbling to be due to under-inflation.
Below is my python code... that I used to run this analysis.
--
import os
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
directory = 'ENTER A DIRECTORY WITH ALL THE CSV FILES HERE'
files = [f for f in os.listdir(directory) if 'csv' in os.path.splitext(f)[1]]
df = None
for file in files:
fullfile = os.path.join(directory,file)
if df is None:
df=pd.read_csv(fullfile)
else:
df=pd.concat([df,pd.read_csv(fullfile)],ignore_index=True)
NEdef = df['def'].str.contains('NE',na=False)
NEoff = df.off.str.contains('NE',na=False)
punts = df.description.str.contains('punts',na=False)
kicks = df.description.str.contains('kicks',na=False)
faircatch = df.description.str.contains('fair catch',na=False)
fumble = df.description.str.contains('FUMBLES',na=False)
touchback = df.description.str.contains('Touchback',na=False)
muff = df.description.str.contains('MUFFS',na=False)
print 'NE def plays',NEdef.sum()
print 'NE off plays',NEoff.sum()
print 'punts',punts.sum()
print 'kicks',kicks.sum()
print 'fumbles',fumble.sum()
print 'muffs',muff.sum()
NEreturns = NEdef & (punts | kicks) & ~faircatch & ~touchback
print 'NEreturns = NEdef & (punts | kicks) & ~touchback & ~faircatch:',NEreturns.sum()
NEreturn_fumbles = NEreturns & fumble
print 'NEreturn & fumble:',NEreturn_fumbles.sum()
notNEreturns = ~NEdef & (punts | kicks) & ~faircatch & ~touchback
print "not NE returns:",notNEreturns.sum()
notNEreturn_fumbles = notNEreturns & fumble
print "not NE returns and fumble:",notNEreturn_fumbles.sum()
print "NE return plays per return fumble:",NEreturns.sum()/NEreturn_fumbles.sum()
print "not NE return plays per return fumble:",notNEreturns.sum()/notNEreturn_fumbles.sum()"