简体   繁体   English

使用VBA在Excel中进行单元格验证的矢量公式

[英]Vectorial formula for cell validation in Excel using VBA

I am writing a VBA formula to check that all characters in a cell "TestChars" are allowed, where allowed means that each character appears in a list defined by another cell "AllowedChars". 我正在编写一个VBA公式,以检查是否允许“ TestChars”单元格中的所有字符,其中允许表示每个字符出现在由另一个单元格“ AllowedChars”定义的列表中。 To make things even harder, I would like this formula to work on ranges of cells rather than on a single cell. 为了使事情变得更加困难,我希望此公式适用于单元格范围而不是单个单元格。

The current code seems to work: 当前代码似乎有效:

Option Explicit


Public Function AllCharsValid(InputCells As Range, AllowedChars As String) As Boolean
' Check that all characters in InputCells are among
' the characters in AllowedChars

    Dim Char As String
    Dim Index As Integer
    Dim RangeTestChars As Range
    Dim TestChars As String
    For Each RangeTestChars In InputCells
        TestChars = RangeTestChars.Value
        For Index = 1 To Len(TestChars)
            Char = Mid(TestChars, Index, 1)
            If InStr(AllowedChars, Char) = 0 Then
                AllCharsValid = False
                Exit Function
            End If
        Next Index
    Next RangeTestChars
    AllCharsValid = True
End Function

I have the following questions: 我有以下问题:

  1. The formula takes a range and returns a single boolean. 该公式采用一个范围并返回一个布尔值。 I would prefer a vectorized function, where, given an input range, you get a corresponding range of booleans. 我希望使用向量化函数,在给定输入范围的情况下,您将获得相应范围的布尔值。 It seems like built-in formulas like 'EXACT' can do this (those formulas where you have to press ctrl-shift-enter to execute them and where you get curly-brackets). 看起来像“ EXACT”之类的内置公式可以做到这一点(那些必须按ctrl-shift-enter才能执行它们并且在大括号中使用的公式)。 Is there a way to do that with user-defined functions? 有没有一种方法可以使用用户定义的功能?
  2. I am not new to programming, however I am completely new to VBA (I started literally today). 我对编程并不陌生,但是对VBA则完全陌生(我从今天开始)。 Is there any obvious problem, weirdness with the above code? 上面的代码有什么明显的问题,很奇怪吗?
  3. Are there special characters, extremely long texts or particular input values that would cause the formula to fail? 是否存在会导致公式失败的特殊字符,超长文本或特定输入值?
  4. Is there an easier way to achieve the same effect? 有没有更简单的方法可以达到相同的效果? Is the code slow? 代码慢吗?
  5. when you start typing built-in formulas in excel you get suggestions and auto-completion. 当您开始在excel中键入内置公式时,您会得到建议和自动完成。 This doesn't seem to work with my formula, am I asking for too much or is it possible to achieve this? 这似乎不适用于我的公式,是我要求太多还是有可能实现这一目标?

I realize that this question contains several weakly related sub-questions, so I would be very happy also with sub-answers. 我意识到这个问题包含几个弱相关的子问题,因此我对子答案也非常满意。

The following code will return a range of boolean values offset one column from the initial input range. 以下代码将返回从初始输入范围偏移一列的布尔值范围。 Simply create a new tab in Excel and run testAllCharsValid and show the Immediate window in the IDE to see how it works. 只需在Excel中创建一个新选项卡,然后运行testAllCharsValid并在IDE中显示“即时”窗口以查看其工作方式。

Sub testAllCharsValid()

    Dim i As Integer
    Dim cll As Range, rng As Range
    Dim allowedChars As String

    ' insert test values in sheet: for testing purposes only
    With ActiveSheet ' change to Thisworkbook.Sheets("NameOfYourSheet")
        Set rng = .Range("A1:A10")
        For i = 1 To 10
            .Cells(i, 1) = Chr(i + 92)
        Next i
    End With

    ' fill allowedChars with letters a to z: for testing purposes only
    For i = 97 To 122
        allowedChars = allowedChars & Chr(i)
    Next i

    ' get boolean range
    Set rng = AllCharsValid(rng, allowedChars)

    ' check if the returned range contains the expected boolean values
    i = 0
    For Each cll In rng
        i = i + 1
        Debug.Print i & " boolean value: " & cll.Value
    Next cll

End Sub

' Check that all characters in InputCells are among
' the characters in AllowedChars
Public Function AllCharsValid(InputCells As Range, allowedChars As String) As Range

    Dim BoolTest As Boolean
    Dim Char As String
    Dim Index As Integer
    Dim RangeTestChars As Range, RangeBooleans As Range, RangeTemp As Range
    Dim TestChars As String
    For Each RangeTestChars In InputCells
        BoolTest = True
        TestChars = RangeTestChars.Value
        For Index = 1 To Len(TestChars)
            Char = Mid(TestChars, Index, 1)
            If InStr(allowedChars, Char) = 0 Then BoolTest = False
        Next Index

        Set RangeTemp = RangeTestChars.Offset(0, 1) ' change offset to what suits your purpose
        RangeTemp.Value = BoolTest

        If RangeBooleans Is Nothing Then
            Set RangeBooleans = RangeTestChars
        Else
            Set RangeBooleans = Union(RangeBooleans, RangeTemp)
        End If

    Next RangeTestChars

    Set AllCharsValid = RangeBooleans

End Function

cf 2) If the length of the test string is zero, the function will return True for the cell in question, which may not be desirable. cf 2)如果测试字符串的长度为零,则该函数将对所讨论的单元格返回True ,这可能不是所希望的。

cf 3) There is a limit to how many characters an Excel cell can contain, read more here . cf 3)Excel单元格可以包含的字符数有限制,请在此处阅读更多内容。 I suppose, if you concatenated some very long strings and sent them to the function, you could reach the integer limit of +32767, which would cause a run-time error due to the integer Index variable. 我想,如果将一些很长的字符串连接起来并发送给函数,则可能会达到+32767的整数限制,由于整数Index变量,这将导致运行时错误。 However, since the character limit of Excel cells is exactly +32767, the function should work as is without any problems. 但是,由于Excel单元格的字符限制恰好是+32767,因此该函数应该可以正常使用而不会出现任何问题。

cf 4) None that I know of. cf 4)我不知道。

cf 5) This is not the easiest thing to achieve, but there is help to be found here . cf 5)这不是最容易实现的方法,但是可以在这里找到帮助。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM