是否存在一个Excel公式来标识单元格中的特殊字符?


13

我们大约有3500个文档,其文件名需要手动清理以删除特殊字符,例如方括号,冒号,分号,逗号等。

我有一个文本文件,该文件已转储到excel中,并且我试图创建一个列,如果包含特殊字符,则该列会标记要修改的文件名。伪代码公式为

=IF (cellname contains [^a-zA-z_-0-9], then "1", else "0")

如果该行包含AZ,0-9,-或_以外的任何字符,则无论其大小写如何,都可以标记该行。

有人知道某些对我有用的东西吗?if如果有任何快速简便的方法,我会犹豫编写代码并发表大量声明。


您在Excel中执行此文本处理任务是否有特定原因?即使只限于Microsoft Office工具,它也是Word中相当简单的搜索和替换。具有两列的表,原始文件名和已处理文件名。
mpez0 2013年

这些是来自第三方软件的索引条目。该软件输出的文件名包括冒号,方括号,“&”号等,导致转换程序中出现异常。转换之前,我们需要清理第三方软件中的数据;供应商未提供用于自动执行该任务的API。我在文本文件中有一个文件名列表。我正在使用Excel创建基于文件名中特殊字符存在的标志。Powershell,c#和Java返回的结果不正确,因为特殊字符被解释为运算符。
dwwilson66 2013年

1
我确实要指出,您可能为此使用了错误的工具。例如,我可以想到几种在Notepad ++中快速完成此操作的方法。您甚至可以在最后将结果导入Excel,并且其列为1s和0s。
戴恩

@Dane很高兴了解NP ++。我将不得不探索。我已经安装了该工具,但是并没有很多经验。谢谢你的提示。
dwwilson66

Answers:


19

没有代码?但这是如此简短,轻松,美丽......(

RegEx模式[^A-Za-z0-9_-]用于删除所有单元格中的所有特殊字符。

Sub RegExReplace()

    Dim RegEx As Object
    Set RegEx = CreateObject("VBScript.RegExp")
    RegEx.Global = True

    RegEx.Pattern = "[^A-Za-z0-9_-]"
    For Each objCell In ActiveSheet.UsedRange.Cells
        objCell.Value = RegEx.Replace(objCell.Value, "")
    Next

End Sub

编辑

这与我对您的原始问题的回答非常接近。

在此处输入图片说明

第二个代码是=RegExCheck(A1,"[^A-Za-z0-9_-]")带有2个参数的用户定义函数。第一个是要检查的单元格。第二个是要检查的RegEx模式。如果模式与您单元格中的任何字符匹配,它将返回1,否则返回0。

如果首先使用ALT+ 打开VBA编辑器F11,然后插入新模块(!)并粘贴以下代码,则可以像使用其他任何普通Excel公式一样使用它。

Function RegExCheck(objCell As Range, strPattern As String)

    Dim RegEx As Object
    Set RegEx = CreateObject("VBScript.RegExp")
    RegEx.Global = True
    RegEx.Pattern = strPattern

    If RegEx.Replace(objCell.Value, "") = objCell.Value Then
        RegExCheck = 0
    Else
        RegExCheck = 1
    End If

End Function

对于RegEx的新用户,我将解释您的模式: [^A-Za-z0-9_-]

[] stands for a group of expressions
^ is a logical NOT
[^ ] Combine them to get a group of signs which should not be included
A-Z matches every character from A to Z (upper case)
a-z matches every character from a to z (lower case)
0-9 matches every digit
_ matches a _
- matches a - (This sign breaks your pattern if it's at the wrong position)

问题是我不想替换字符,只是在列表上标记它们,以便我可以将其交给其他人。文件名是由第三方软件创建的,需要在该程序中手动更改...我只需要标记是或否。话虽如此,我想我可以修改您的替换代码来标记该列。:)
dwwilson66

来实现这个...只是剪切和粘贴到新模块中并保存的问题,对吗?还是我需要做其他事情?该公式=RegExReplace(cell)无法识别....而我在创建新函数时有些生疏。
dwwilson66

@ dwwilson66更新!
nixda 2013年

强调RegEx内的连字符(如果位置错误,此符号会破坏您的图案)
红豆2015年

7

使用类似于nixda的代码的方法,这是一个用户定义的函数,如果单元格中有特殊字符,该函数将返回1。

Public Function IsSpecial(s As String) As Long
    Dim L As Long, LL As Long
    Dim sCh As String
    IsSpecial = 0
    For L = 1 To Len(s)
        sCh = Mid(s, L, 1)
        If sCh Like "[0-9a-zA-Z]" Or sCh = "_" Then
        Else
            IsSpecial = 1
            Exit Function
        End If
    Next L
End Function

用户定义函数(UDF)易于安装和使用:

  1. ALT-F11弹出VBE窗口
  2. ALT-I ALT-M打开一个新模块
  3. 将内容粘贴并关闭VBE窗口

如果保存工作簿,则UDF将随其一起保存。如果要在2003年以后使用Excel版本,则必须将文件另存为.xlsm而不是.xlsx

删除UDF:

  1. 如上调出VBE窗口
  2. 清除代码
  3. 关闭VBE视窗

要从Excel使用UDF:

=特殊(A1)

要总体上了解有关宏的更多信息,请参见:

http://www.mvps.org/dmcritchie/excel/getstarted.htm

http://msdn.microsoft.com/zh-CN/library/ee814735(v=office.14).aspx

http://www.cpearson.com/excel/WritingFunctionsInVBA.aspx

有关UDF的细节

必须启用宏才能使其正常工作


为什么将“ _”用作单独的“或”项目?它可以包含在同一[]组中
jstuardo

@jstuardo仅是为了清楚表明下划线是有效字符。
加里的学生

不应将代码更新If sCh Like "[0-9a-zA-Z ]" Or sCh = "_" Then为该宏,以便假定空格是有效字符吗?
Ovaryraptor

@Ovaryraptor你是对的!我明天会更新。
加里的学生

2

这是一个条件格式解决方案,它将用特殊字符标记记录。

只需对使用以下(极长)公式的数据应用新的条件格式设置规则,该规则A1就是文件名列中的第一条记录:

=SUMPRODUCT((CODE(MID(A1,ROW(INDIRECT("1:"&LEN(A1))),1))<48)*(CODE(MID(A1,ROW(INDIRECT("1:"&LEN(A1))),1))<>45))+SUMPRODUCT((CODE(MID(A1,ROW(INDIRECT("1:"&LEN(A1))),1))>57)*(CODE(MID(A1,ROW(INDIRECT("1:"&LEN(A1))),1))<65))+SUMPRODUCT((CODE(MID(A1,ROW(INDIRECT("1:"&LEN(A1))),1))>90)*(CODE(MID(A1,ROW(INDIRECT("1:"&LEN(A1))),1))<97)*(CODE(MID(A1,ROW(INDIRECT("1:"&LEN(A1))),1))<>95))+SUMPRODUCT((CODE(MID(A1,ROW(INDIRECT("1:"&LEN(A1))),1))>122)*1)

此公式检查每个文件名的每个字符,并确定其ASCII码是否在允许的字符值之外。不幸的是,允许的字符代码并不都是连续的,因此这就是公式必须使用SUMPRODUCTs之和的原因。该公式返回存在的不良字符数。任何返回值大于0的单元格都会被标记。

例: 在此处输入图片说明


1

我使用了另一种方法来查找特殊字符。我为每个允许的字符创建了新列,然后使用如下公式来计算每个行条目(Z2)中允许的字符有多少次:

AA2=LEN($Z2)-LEN(SUBSTITUTE($Z2,AA$1,""))
AB2=LEN($Z2)-LEN(SUBSTITUTE($Z2,AB$1,""))
...

然后,我对每一行中允许的字符数求和,然后将其与行条目的总长度进行比较。

BE2=LEN(Z2)
BF2=SUM(AA2:BC2)-BE2

最后,我在最后一列(BF2)上排序以找到负值,这使我进入需要更正的列。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.