
又到了每个月算绩效的时候。你面前这张评分表二十个评委打分平均值算出来3.8分看起来还行突然有个评委给了一两个极端低分平均分立刻被拽下来整个部门的绩效排序跟着乱套。这种被极端数字绑架的场景Excel里其实有一个专门应对的函数TRIMMEAN。TRIMMEAN的核心逻辑就是去除极端值后再做平均——先把数据按大小排序按照你指定的比例从头部和尾部对称剪掉一定数量的数据点再对剩余数据求平均值比手工删掉最高最低分再计算要严谨得多。这篇文章我打算把TRIMMEAN的语法规则、不同平均算法的选型逻辑、实际案例和常见翻车点一次讲透适合正在做绩效考核、销售分析、竞赛评分、实验数据处理的Excel用户参考。1. TRIMMEAN删数据的数学规则percent参数与截断数量1.1 percent参数你到底想让Excel丢掉几个数第一次用TRIMMEAN的人十有八九会被第二个参数绕晕。先看语法TRIMMEAN(array, percent)array要计算平均值的数据区域比如A1:A20。percent要从数据集中剔除的数据点比例取值在0到1之间。注意这里的核心词是“比例”不是“个数”。一个很常见的错误是我想去掉一个最高分和一个最低分所以写TRIMMEAN(B2:G2, 2)。这个写法一定会让你收到一个#NUM!错误因为percent2已经超出了Excel允许的合理区间。正确理解是这样percent0.2表示整个数据集里20%的数据会被排除这20%不是只砍一边而是对称分配——最小的10%砍掉最大的10%也砍掉两头各10%。所以对10个数来说TRIMMEAN(A1:A10,0.2)的真正效果是先排序把最小的1个数和最大的1个数丢出去中间8个数求平均。再换个角度TRIMMEAN和“手动删除最高最低后计算平均”不是一回事。手动删除是固定个数而TRIMMEAN是固定比例。如果你面对的是20个数据设置0.2那么整体会排除20×0.24个数即头尾各2个剩下16个参与平均。数据量越大同样比例下被排除的个数越多。1.2 向下取偶的截断逻辑为什么不是四舍五入很多人会问设了比例之后Excel到底是怎么决定剪掉几个数的我查过微软官方文档内部规则可以概括成三步计算数据总数 × percent得到一个候选数。把这个候选数向下取整到最近的偶数。用这个偶数除以2得到“头部剔除数量”和“尾部剔除数量”。举个例子数据总数是15percent0.2那么15×0.23。为什么最后不是剪掉3个而是剪掉2个因为3向下取偶是2于是头尾各剪1个总共剪2个。这看起来有点“奇怪”但逻辑上很好理解要保证头尾对称每次剔除必须成对进行。如果剪掉3个就无法做到头尾各占1.5个。这个细节让很多人在验证公式时产生困惑。比如你手算“15个数据剪掉20%”预期是3个结果发现TRIMMEAN只剪了2个于是怀疑函数算错了。其实没算错是“就近取偶”规则在起作用。可以把它想象成Excel为了保持剪刀平衡只能成双地剪奇数个的修剪请求会被自动降级到最近的偶数。1.3 一份常用比例速查表直接对着用就行下面的表总结了不同数据量和不同percent下真正被排除的数据点个数数据总数percent设置总数×percent向下取偶结果头尾各去剩余参与平均的个数100.110010100.22218150.232113200.244216200.366314300.132128300.266324注意第一行数据总数10、percent0.1时10×0.11向下取偶得到0所以一个数据都不会剪。如果你拿到一组8条记录设置percent0.1同样因为8×0.10.8向下取偶还是0函数等于什么都没干。这类“设置了比例但没有效果”的情况在第4章会专门展开讲。理解了上述规则之后TRIMMEAN的行为就完全可以预测了后续排错也就有了抓手。2. 三种均值怎么选TRIMMEAN、AVERAGE、MEDIAN的实战对比2.1 同一组数据三种平均算出来差多少我经常在培训里用一组数据说明三个函数的差别。假设你收到这样10个数1, 2, 30, 31, 32, 33, 34, 35, 36, 100分别计算三种结果计算方式结果解读AVERAGE33.4被100明显拉高也受到左侧1、2的拖累MEDIAN32.5只看中间位置稳健但完全忽略两头数据TRIMMEAN(区域,0.2)29去掉排序后最小的1和最大的100剩下8个求平均TRIMMEAN在这里得到一个更贴近“大众水平”的29。它没有像MEDIAN那样只取一个位置而是保留了中间80%数据的全部信息同时把两端最极端的10%各甩掉。再举个评分的直觉例子。6个评委给分如下2, 6, 7, 8, 9, 10AVERAGE 7被那个2分拉得明显偏低。TRIMMEAN(区域,0.2)6×0.21.2向下取偶后是0等等这里不能直接取0。重新算6×0.21.2向下取偶到0一个都不剪。哦这个例子不对换TRIMMEAN(区域,0.3333)不行。用评委例子时如果6个评委要去掉最高最低各一个应该用TRIMMEAN(区域,2/6)6×(2/6)2向下取偶2头尾各去1剩下6、7、8、9平均7.5。这比直接平均的7更合理也更接近“去掉一个最高分、去掉一个最低分”的竞赛规则。所以实际工作中TRIMMEAN的价值在于它不会像AVERAGE那样被个别妖孽数据牵着走也不会像MEDIAN那样完全放弃数据的数值大小信息而是通过按比例修剪得到一个更稳、但又保留了大部分真实数据信息的中心趋势值。2.2 我的选型判断标准什么样的场景适合TRIMMEAN我一般用下面这个判断清单数据里存在明显离群点你又不想主观决定“到底删哪个数”。数据量较大且极端值属于“噪音”而非研究对象。比如评委打分、销售流水、设备测量值、用户体验评分。希望通过固定比例统一处理一批数据让规则透明可复现——这正是绩效考核最看重的一点。数据结构比较干净没有大量文本、空值和错误值混入。反过来这几种情况别用数据量太小。总共3到5个数据再剪掉一两个剩余样本信息太少结果可能还不如直接用中位数。极端值本身就是业务关注对象。比如做风险分析时最大损失金额恰恰是最重要的指标剪掉它就等于把核心信息弄丢了。合同、制度、审计要求明确规定了算法不能用替代性算法。你需要保证所有数据点都被纳入统计口径哪怕它是异常的。2.3 判断数据是否被极端值绑架的快速检查法动手写TRIMMEAN之前可以先花三秒钟做个预检判断这组数据是不是真的需要修剪。我常用的办法是看平均值和中位数的差值ABS(AVERAGE(D2:D31) - MEDIAN(D2:D31))如果这个差值相对数据本身的量级很大比如平均值30中位数15差了整整一倍那说明极端值影响相当严重。此时用TRIMMEAN就非常合适。如果两者本来就接近说明数据分布比较正常用普通AVERAGE也没什么问题。也可以用条件格式快速可视化选中数据区域添加“数据条”或“箱线图”类型的图表一眼就能看出有没有明显脱离群体的点。判断做完再决定修剪比例比直接套一个0.1或0.2要靠谱得多。3. 分数去极值与销售清洗两个可直接抄走的实例3.1 六位评委打分的去高去低平均分场景你有一张员工评分表B列到G列是6位评委的打分H列要算“去掉一个最高分、去掉一个最低分后的平均分”。第一版公式可以这样写TRIMMEAN(B2:G2, 2/COUNT(B2:G2))这里2/COUNT(B2:G2)的意思很明确要剔除2个数占总数的比例就是2除以评委人数。对于6位评委percent2/6≈0.3333数据总数×percent6×0.3333≈2向下取偶仍是2于是头尾各剪1个剩下的4个数求平均。关键在于COUNT是动态计算的如果某位员工只有5位评委打分公式会自动变成2/5不需要手动改。但这里有一个天然的边界问题如果评委人数只有1个或2个2/COUNT会大于等于1TRIMMEAN会直接返回#NUM!。所以实际落地时我给业务部门的模板公式通常会加一层防护IF(COUNT(B2:G2)3, TRIMMEAN(B2:G2, 2/COUNT(B2:G2)), AVERAGE(B2:G2))当评委不足3人时一律用普通平均3人及以上才启用修剪逻辑。这在实际考核场景里很关键——你不希望一个五六个评委的季度考核因为某个员工请假导致只有2个评委打分整列公式报错最后交上去一张红红绿绿的表。如果你特别排斥这种动态百分比写法也可以用更传统的数组公式思路是直接取中间段数据求平均AVERAGE(SMALL(B2:G2, ROW(INDIRECT(2:COUNT(B2:G2)-1))))老版本Excel需要按CtrlShiftEnter确认输入。这个公式能精确做到“去掉最小一个、去掉最大一个”不依赖比例换算。但它的缺点是计算逻辑不直观看公式的人不容易理解。所以我个人还是更推荐TRIMMEAN加COUNT的方案业务部门拿到公式自己也能看懂去掉2个数所以比例是2除以人数。3.2 销售明细表里按店剔除异常订单另一个高频场景是销售数据清洗。假设你有一家门店30天的日销售额在B2:B31区域想剔除最大一笔和最小一笔之后看日均。公式照样是TRIMMEAN(B2:B31, 2/COUNT(B2:B31))30天乘2/30等于2取偶后还是2头尾各去1笔。这样得到的日均销售比直接AVERAGE更抗干扰。某天大客户突然来了一笔50万的大单如果把这一天保留在均值里整月分析都会失真直接删掉这一天又有点“人为干预”的嫌疑。用TRIMMEAN给出一个透明规则所有人都知道是“按比例自动剔除”讨论成本低很多。这里分享一个容易踩的坑分母千万别用COUNTA。COUNTA会统计非空单元格一旦销售明细列里有导入进来的文本说明、备注信息COUNTA会把它们也数进去导致percent偏大修剪量超出预期。而COUNT只数数值和TRIMMEAN的忽略文本规则能对齐。如果数据里存在空行也要小心区域引用范围。比如B2:B200选了很大一片区域中间某些天没数据TRIMMEAN在计算时会忽略空单元格但COUNT(B2:B200)也只数有数值的单元格所以百分比计算依然能对齐这算是TRIMMEAN比较智能的地方。不过最好还是把区域范围收窄到实际数据区域避免后续添加备注列时干扰公式。3.3 按组剔除极值的进阶写法销售分析常常不只看整个表可能要看每个业务员、每个门店自己的均值。这时候就有人问TRIMMEAN有没有像AVERAGEIF那样的条件版本很遗憾TRIMMEAN没有条件版函数。但如果你用的是Excel 365可以利用FILTER函数先取出某个业务员的数据再丢给TRIMMEANTRIMMEAN(FILTER(C$2:C$1000, A$2:A$1000E2), 2/COUNT(FILTER(C$2:C$1000, A$2:A$1000E2)))这个公式的意思是从C列里筛出业务员等于E2的所有销售额然后按2除以对应数量的比例做修剪均值。E2是某个业务员的名字下拉填充就能算完所有人。老版本Excel没有FILTER我用过两种替代方案一是加辅助列先用IF生成一组只保留目标业务员数值的辅助列再对辅助列套TRIMMEAN二是使用数组公式配合INDEX和SMALL。辅助列虽然多占一列但对业务同事最友好因为他们能直观看到哪些数被剔除了。自动化程度要求高时再推荐直接交给Python处理这个在文章第5章展开。4. 容易翻车的边界情况percent、脏数据与隐藏行4.1 percent参数的四个常见报错原因TRIMMEAN的报错不算多但每种报错都对应着一个真实使用场景。我梳理一份常见报错对照表错误值常见原因修复思路#NUM!percent小于0或大于等于1检查percent参数尤其要确认没有把“2”直接写成第二个参数#DIV/0!区域内没有数值全是文本或空单元格先清洗数据用COUNT检查数值数量#N/A区域里有错误值被函数捕捉修复来源或先将错误值替换为空白再处理#VALUE!直接使用包含文本的常量数组例如TRIMMEAN({1,2,a},0.2)尽量使用单元格区域引用而不是手写数组常量这里我要单独强调一下percent1的坑。某个同事的做法是把百分比直接输入成20因为单元格恰好是百分比格式他以为20就是20%。但Excel内部实际存储的是20不是0.2TRIMMEAN直接返回#NUM!。正确的做法是输入0.2或者输入20%并让Excel在内部自动保存为0.2。判断方法很简单点一下该单元格看编辑栏里显示的是0.2还是20后者就要重新输入。4.2 数据量太小导致“白剪”有朋友问我我明明设置了10%的修剪比例为什么结果跟平均分完全一样很可能是数据的数量级太小了。比如8个数据8×0.10.8向下取偶后是0等于一个没剪。这不是函数bug而是前面说的“向下取偶”规则造成的必然结果。知道了这个规则就能提前预判想剪头尾各一个数至少要让数据总数×percent落在2到4这个区间。最简单的解法是改用动态比例比如明确要剪2个数就用2/COUNT(区域)而不是纠结写0.1还是0.2。话说回来如果数据总数只有6个、8个与其不停调percent不如直接考虑用中位数或固定掐头去尾的SMALL组合公式至少在业务沟通上更直接。4.3 文本、错误值与隐藏行脏数据入场前的预检TRIMMEAN在区域引用情况下会遵循Excel统计函数的一般规则忽略文本、逻辑值和空单元格。这不是什么问题。真正的问题是错误值比如#N/A或#DIV/0!它们不会像文本那样被忽略而是会直接传染给TRIMMEAN的最终结果。一个区域里只要有一个#N/A整个结果就不可能算出来。另外很多人忽略的一点TRIMMEAN不会忽略隐藏行。它和SUBTOTAL完全不同。我有一次做报表为了比对效果手工隐藏了几行评分最低的记录然后发现TRIMMEAN的结果纹丝不动还以为表格没刷新。实际情况是隐藏行照样参与修剪和平均计算。如果你确实只想对可见行进行计算就得先把数据筛选好再复制到新区域或者改用SUBTOTAL配合辅助列实现。再提一句文本型数字。从系统导出的Excel经常出现那种左上角带绿色三角的文本型数字。它们看起来是数字但TRIMMEAN在忽略文本的规则下会把它们当空气导致数值数量比肉眼看到的少。解决方法也简单选中整列用“分列”功能直接点完成或者用选择性粘贴乘1把文本型数字强制转成数值。这也是我接手业务报表时第一个检查的动作。4.4 我的#DIV/0!排错记录去年帮运营部门处理过一张门店销售评分表打开之后满屏#DIV/0!一片红。第一反应以为是percent参数有问题点进去看公式0.2写得好好的奇怪。我用三个步骤定位先用COUNT检查区域内的数值数量结果显示0。再用COUNTA检查非空单元格数量结果显示有78。马上意识到这78个单元格全是文本型数字或者字符串根本没有真正的数值。最后发现这批数据是从某个内部系统导出后又经过了文本拼接处理所有数字都变成了文本。修复过程并不复杂对销售列执行“分列”用固定宽度或分隔符方式直接完成转换再刷新公式结果全部正常。这次排错让我养成了一个习惯任何统计类函数返回异常时永远先怀疑数据源而不是先怀疑函数本身。如果你也遇到类似问题可以先在某空白单元格输入COUNT(区域)看看返回的是不是预期的数值个数就能快速判断数据里有没有隐藏的文本暗雷。5. 跳出Excel看截尾均值Python复现与Power Query辅助方案5.1 截尾均值在统计学里的定位TRIMMEAN在统计学里有个正式名字截尾均值或者叫修剪均值。它属于稳健统计里的一类位置估计量。稳健的意思是当我们的数据中存在少量离群点时统计结果不会被这些点带偏得太严重。普通均值虽然效率高但对极端值极其敏感中位数虽然稳健却会放弃很多数值信息。截尾均值正好站在两者中间通过“按比例去掉两端”实现一种温和的稳健性。理解了这层背景你就会明白为什么TRIMMEAN的参数设计成“比例”而不是“个数”。比例的形式天然允许它适配不同数据量从20条到2万条都能用同一个规则这在大规模数据自动处理里非常关键。5.2 Python一行代码复现TRIMMEAN逻辑在Python里复现TRIMMEAN很简单用scipy.stats.trim_mean。但这里有一个相当于“魔鬼细节”的差异我必须单独拎出来讲Excel的TRIMMEAN(数据, 0.2)表示整体剔除20%也就是头尾各10%。Python的scipy.stats.trim_mean(数据, proportiontocut0.2)表示每一边各剔除20%整体剔除40%。如果你把Excel里的0.2原封不动搬到Python算出来的结果会跟你预想的完全不一样。正确的对应写法是from scipy.stats import trim_mean data [1, 2, 30, 31, 32, 33, 34, 35, 36, 100] result trim_mean(data, proportiontocut0.1) # 相当于是Excel的0.2 print(result) # 29.0这个例子和第2章那个表对应上了python结果同样等于29。所以跨工具核对时先确认“你的0.2到底是指单边还是双边比例”这是很多人踩过的最痛的坑。5.3 批量Excel自动化pandas加trim_mean的清洗模板日常处理几十行用Excel公式完全够了。但当你要对几十个Excel文件、上万行数据做统一修剪均值时逐行下拉公式反而低效。这时候我习惯直接用Python写个小脚本一次性把数据读进来、算好、写回去既省时间又不容易漏。下面是一个可以直接修改使用的模板。假设你手头有一张Excel表格里面有多位员工的评分数据列结构是姓名加多个评分列你要在最后新增一列“修剪均值”统一按20%整体比例做截尾import pandas as pd from scipy.stats import trim_mean df pd.read_excel(评分表.xlsx, sheet_nameSheet1) # 假设前1列是姓名后面的都是评分列 score_cols df.columns[1:] # 按行计算基准比例按Excel的0.2换算成Python的0.1 df[修剪均值] df[score_cols].apply( lambda row: trim_mean(row.dropna().values, proportiontocut0.1), axis1 ) df.to_excel(评分表_输出.xlsx, indexFalse)注意这里我用row.dropna()把空值先去掉避免trim_mean因为空值返回NaN。另外proportiontocut0.1是Excel里0.2的对应值如果你要改比例记住“Excel percent除以2”就是Python单边比例。写回Excel需要依赖openpyxl或xlsxwriter安装时一步到位即可pip install pandas scipy openpyxl如果你不想引入scipy只想用pandas思路也很直接排序后手工掐头去尾再求平均。但既然scipy一行就能解决没必要自己造轮子。5.4 Power Query里的无内置替代方案Power Query目前没有直接的TRIMMEAN函数。如果你正在搭建自动刷新报表又不想返回Excel算可以用一段简单的M语言自定义函数。逻辑就是先排序再按比例掐头去尾最后取平均。整体代码如下(values as list, percent as number) let sortedList List.Sort(values), count List.Count(sortedList), excludeCount Number.IntegerFloor(count * percent / 2) * 2, keptList List.Range(sortedList, excludeCount / 2 / 1 0, count - excludeCount), result List.Average(keptList) in result需要说明的是这只是对齐Excel剔除逻辑的一种M语言近似实现边界情况和浮点细节未必能完全一致。在Power Query里做快速探索性分析可以真要交付正式报表我更建议先把数据源清洗干净再回到Excel或Python里用成熟函数计算。在我看来TRIMMEAN的价值不在于它多复杂而在于它帮你把“剪掉极端值”这件事从拍脑袋变成了可解释、可复制的规则。最后再分享一个我个人的小习惯每次用TRIMMEAN之前先选中数据源区域按F9或直接看状态栏的平均值再对比TRIMMEAN的结果两张数字一对照你对这批数据的分布就有数了。数据越脏、口径越不统一这个习惯越能帮你提前躲开后面一整片麻烦。