ExcelHome技术论坛

 找回密码
 免费注册

QQ登录

只需一步,快速开始

快捷登录

搜索
EH技术汇-专业的职场技能充电站 妙哉!函数段子手趣味讲函数 Excel服务器-会Excel,做管理系统 Excel Home精品图文教程库
HR薪酬管理数字化实战 Excel 2021函数公式学习大典 Excel数据透视表实战秘技 打造核心竞争力的职场宝典
300集Office 2010微视频教程 数据工作者的案头书 免费直播课集锦 ExcelHome出品 - VBA代码宝免费下载
用ChatGPT与VBA一键搞定Excel WPS表格从入门到精通 Excel VBA经典代码实践指南
楼主: WYS67

[求助] 按数值从大到小返回前一二三名对应序号的自定义函数

[复制链接]

TA的精华主题

TA的得分主题

 楼主| 发表于 2019-7-19 06:22 | 显示全部楼层
本帖最后由 WYS67 于 2019-7-19 11:09 编辑

表一.gif

前三排名.zip (706.37 KB, 下载次数: 4)

老师:由于我拙嘴笨舌,叙述的不清楚,给您造成了误会,真是对不起!

    38楼附件存在的问题是:当I586:K586【最后数据行】以下没有数据时,应该屏蔽S587:U587以下为空白才对;【I5:K1468】

     如上面左图所示的问题--数据源I5:K589列的数据区域里,其中有18行没有数据;而数据区域的最后行号是I589:K589,用了40楼的代码后,从数据区域第一个空行对应的M44以下都显示成了空白。

     我需要的是:让数据区域【I5:K1468】的最后数据行【I589:K589】对应的M589以下显示空白而M44:M589仍须按运算规则显示结果


   老师可根据附件O5:O45的原代码,进行修改。附原代码:

Function Q3PM(rgData As Range, Optional arrIndex As Variant = 4) As Variant
    Dim arrTitle As Variant, arrData As Variant, rgCur As Range
    Dim lngRow As Long, lngCol As Long, lngCols As Long, intLen As Integer
    Dim lngVal() As Long, strVal() As String
    Dim arrResult As Variant, arrReturn As Variant, lngID As Long
    Dim lngIndex As Long, strTemp(1 To 3) As String, strAll As String

    Application.Volatile True

    lngCols = rgData.Columns.Count
    If lngCols < 3 Then Exit Function '小于3列退出

    ReDim lngVal(1 To lngCols) As Long, strVal(1 To lngCols) As String

    arrTitle = rgData.Offset(-1, 0).Resize(1) '标题区域是数据区域的上一行
    arrData = rgData
    lngID = arrIndex

    Set rgCur = Application.Caller
    ReDim arrResult(1 To rgCur.Rows.Count, 1 To 4) As String
    Set rgCur = Nothing

    For lngRow = LBound(arrData) To UBound(arrData)
        If arrData(lngRow, 1) = "" Then Exit For
        For lngCol = 1 To lngCols
            strVal(lngCol) = Format(arrData(lngRow, lngCol), "00") & strVal(lngCol)
            lngVal(lngCol) = Val(Trim(Mid(strVal(lngCol), 1, 6)) & Format(lngCol, "00"))
        Next

        lngIndex = lngIndex + 1: strAll = ""
        For lngCol = 1 To 3
            strTemp(lngCol) = Right(CStr(Application.WorksheetFunction.Large(lngVal, lngCol)), 2)
            strAll = strAll & arrTitle(1, strTemp(lngCol))
            arrResult(lngIndex, lngCol) = arrTitle(1, strTemp(lngCol))
        Next
        arrResult(lngIndex, 4) = strAll
    Next

    arrReturn = Application.WorksheetFunction.Index(arrResult, 0, lngID)
    Q3PM = arrReturn
End Function



TA的精华主题

TA的得分主题

 楼主| 发表于 2019-7-19 10:50 | 显示全部楼层
[广告] Excel易用宝 - 提升Excel的操作效率 · Excel / WPS表格插件       ★免费下载 ★       ★ 使用帮助
恳请老师帮忙解决44楼反映的问题。

TA的精华主题

TA的得分主题

发表于 2019-7-19 12:03 | 显示全部楼层
问题有多方面,修改了另外一个函数,确保不会有多余的0返回,然后,再修改本次的函数,找到有内容的最后一行,详见附件
前三排名.rar (685.89 KB, 下载次数: 7)

评分

1

查看全部评分

TA的精华主题

TA的得分主题

 楼主| 发表于 2019-7-19 12:56 | 显示全部楼层
lsdongjh 发表于 2019-7-19 12:03
问题有多方面,修改了另外一个函数,确保不会有多余的0返回,然后,再修改本次的函数,找到有内容的最后一 ...

1.gif
前三排名.zip (708.83 KB, 下载次数: 3)

首先,万分感谢老师的帮忙!  如截图所示,发现M列有许多结果没有按照原来的运算规则进行计算,N列里新增加的数据才是M列本行应该显示的正确结果。我需要的是:让数据区域【I5:K1468】的最后数据行【I589:K589】对应的--M589以下显示空白,而M5:M589仍须按原运算规则显示计算结果

  如果修改实在困难,那我就还按照原有的代码进行计算【如38楼截图所示,虽然S587:T587运行多了不必要的数据,但是S5:T586之间显示的计算结果倒是正确!】


再次感谢老师的热心帮忙!


TA的精华主题

TA的得分主题

发表于 2019-7-19 13:33 | 显示全部楼层

TA的精华主题

TA的得分主题

 楼主| 发表于 2019-7-19 13:52 | 显示全部楼层
[广告] Excel易用宝 - 提升Excel的操作效率 · Excel / WPS表格插件       ★免费下载 ★       ★ 使用帮助
lsdongjh 发表于 2019-7-19 13:33
不支持负数!!!组合不了

老师,您这一提醒让我恍然大悟--现在回想起来,您写的XHCOUNTIF和Q3PM函数,原先一直都能显示正确结果,就是在这个有负数存在的附件里才第一次出现了错误。

我可以修改《总表》AN列的公式,避免计算结果出现负数。

再次感谢您的提醒!

TA的精华主题

TA的得分主题

 楼主| 发表于 2019-7-23 19:28 | 显示全部楼层
[广告] Excel易用宝 - 提升Excel的操作效率 · Excel / WPS表格插件       ★免费下载 ★       ★ 使用帮助
本帖最后由 WYS67 于 2019-7-24 07:43 编辑
lsdongjh 发表于 2019-7-19 12:03
问题有多方面,修改了另外一个函数,确保不会有多余的0返回,然后,再修改本次的函数,找到有内容的最后一 ...

没有加载宏.gif 已加载宏.gif

前三排名.zip (672.12 KB, 下载次数: 11)

老师:请看截图--同样的代码,上图没有加载宏,由于数据源I615:R615以下没有数据,所以S615以下显示正确的空白;而加载宏后的下图,尽管数据源I615:R615以下没有数据,但S615:S936仍然显示数字,而没有显示空白!

辅助列V列是I:R列每一行的数字和,自V615以下为0,我把W列的公式加了个判断条件,选定W5:W1468,输入区域数组公式 {  =IF(SUM(V5:V1468)=0,"",Q3PM($I$5:$R$1468,1))   ,这样无论有没有加载宏,W列都能显示正确的结果【也就是由于I615:R615以下数据和为0,所以W615以下显示空白】!

老师:能不能这样--在代码里增加一个判断条件,当数据区域的任意一行和值为0时,强制使Q3PM对应行的计算结果为空白?如此,则可彻底解决数据源I615:R615以下没有数据,但S615:S936仍然显示数字的问题!

如果此方法可行,您看加在下面代码的哪个地方合适?

Function Q3PM(rgData As Range, Optional arrIndex As Variant = 4) As Variant
    Dim arrTitle As Variant, arrData As Variant, rgCur As Range
    Dim lngRow As Long, lngCol As Long, lngCols As Long, intLen As Integer
    Dim lngVal() As Long, strVal() As String, strALL As String
    Dim arrResult As Variant, arrReturn As Variant, lngID As Long
    Dim lngIndex As Long, strTemp(1 To 3) As String, strIsNull As String

    Application.Volatile True

    lngCols = rgData.Columns.Count
    If lngCols < 3 Then Exit Function '小于3列退出

    ReDim lngVal(1 To lngCols) As Long, strVal(1 To lngCols) As String

    arrTitle = rgData.Offset(-1, 0).Resize(1) '标题区域是数据区域的上一行
    arrData = rgData
    lngID = arrIndex

    Set rgCur = Application.Caller
    ReDim arrResult(1 To rgCur.Rows.Count, 1 To 4) As String
    Set rgCur = Nothing

    For lngRow = LBound(arrData) To UBound(arrData)
        If arrData(lngRow, 1) = "" Then Exit For
        strIsNull = ""
        For lngCol = 1 To lngCols
            strIsNull = strIsNull & arrData(lngRow, lngCol)
            strVal(lngCol) = Format(arrData(lngRow, lngCol), "00") & strVal(lngCol)
            lngVal(lngCol) = Val(Trim(Mid(strVal(lngCol), 1, 6)) & Format(lngCol, "00"))
        Next
        If Val(strIsNull) = 0 Then Exit For
        lngIndex = lngIndex + 1: strALL = ""
        For lngCol = 1 To 3
            strTemp(lngCol) = Right(CStr(Application.WorksheetFunction.Large(lngVal, lngCol)), 2)
            strALL = strALL & arrTitle(1, strTemp(lngCol))
            arrResult(lngIndex, lngCol) = arrTitle(1, strTemp(lngCol))
        Next
        arrResult(lngIndex, 4) = strALL
    Next

    arrReturn = Application.WorksheetFunction.Index(arrResult, 0, lngID)
    Q3PM = arrReturn
End Function

TA的精华主题

TA的得分主题

 楼主| 发表于 2019-7-24 08:33 | 显示全部楼层
[广告] Excel易用宝 - 提升Excel的操作效率 · Excel / WPS表格插件       ★免费下载 ★       ★ 使用帮助
也就是在代码中判断条件:当数据源I:R的任意一行全部为空全部为0时,结果输出列的对应行显示为空白!

TA的精华主题

TA的得分主题

 楼主| 发表于 2019-7-24 09:54 | 显示全部楼层
[广告] Excel易用宝 - 提升Excel的操作效率 · Excel / WPS表格插件       ★免费下载 ★       ★ 使用帮助
请在50楼原代码中合适的地方,添加一句判断---当数据源I:R列的任意一行全部为空或全部为0时,结果输出列的对应行显示为空白!

TA的精华主题

TA的得分主题

 楼主| 发表于 2019-7-24 12:40 | 显示全部楼层
请在50楼原代码中合适的地方,添加一句判断---当数据源I:R列的任意一行全部为空或全部为0时,结果输出列的对应行显示为空白!
您需要登录后才可以回帖 登录 | 免费注册

本版积分规则

关闭

最新热点上一条 /1 下一条

手机版|关于我们|联系我们|ExcelHome

GMT+8, 2024-4-19 14:48 , Processed in 0.039618 second(s), 10 queries , Gzip On, MemCache On.

Powered by Discuz! X3.4

© 1999-2023 Wooffice Inc.

沪公网安备 31011702000001号 沪ICP备11019229号-2

本论坛言论纯属发表者个人意见,任何违反国家相关法律的言论,本站将协助国家相关部门追究发言者责任!     本站特聘法律顾问:李志群律师

快速回复 返回顶部 返回列表