用空格替换Unicode字符“�”

8

我正在从.csv文件中进行大批量信息上传,需要将这个非ASCII字符“�”替换为普通空格,“ ”。

字符“�”在C、C++和Java中对应“\uFFFD”,它似乎被称为REPLACEMENT CHARACTER。还有其他类型的空格,如U+FEFFU+205FU+200BU+180EU+202F在C#的官方文档中。

我尝试用以下方式进行替换:

public string Errors = "";

public void test(){

    string textFromCsvCell = "";
    string validCharacters = "^[0-9A-Za-z().:%-/ ]+$";
    textFromCsvCell = "This is my text from csv file"; //All spaces aren't normal space " "
    string cleaned = textFromCsvCell.Replace("\uFFFD", "\"")
      if (Regex.IsMatch(cleaned, validCharacters ))
        //All code for insert
      else
         Errors=cleaned;
         //print Errors
}

测试方法显示给我这个文本:

"这是来自CSV文件的我的文本"

我也尝试了一些解决方案:

尝试解决方案1:使用Trim

 Regex.Replace(value.Trim(), @"[^\S\r\n]+", " ");

尝试解决方案2:使用替换。
  System.Text.RegularExpressions.Regex.Replace(str, @"\s+", " ");

尝试解决方案3:使用Trim
  String.Trim(new char[]{'\uFEFF', '\u200B'});

尝试解决方案4:在validCharacters中添加[\S\r\n]。
  string validCharacters = "^[\S\r\n0-9A-Za-z().:%-/ ]+$";

什么都不起作用。

我该如何替换它?

参考资料:

编辑

这是原始字符串:

"SYSTEM OF MONITORING CONTINUES OF GLUCOSE"

以0x...表示法

SYSTEM OF0xA0MONITORING CONTINUES OF GLUCOSE

解决方案

转到Unicode代码转换器。查看转换并进行替换

在我的情况下,我进行了简单的替换:

 string value = "SYSTEM OF MONITORING CONTINUES OF GLUCOSE";
 //value contains non-breaking whitespace
 //value is "SYSTEM OF�MONITORING CONTINUES OF GLUCOSE"
 string cleaned = "";
 string pattern = @"[^\u0000-\u007F]+";
 string replacement = " ";

 Regex rgx = new Regex(pattern);
 cleaned = rgx.Replace(value, replacement);

 if (Regex.IsMatch(cleaned,"^[0-9A-Za-z().:<>%-/ ]+$"){
    //all code for insert
 else
    //Error messages

这个表达式表示所有可能的空格:空格,制表符,分页符,换行符和回车符。
[ \f\n\r\t\v​\u00a0\u1680​\u180e\u2000​\u2001\u2002​\u2003\u2004​\u2005\u2006​\u2007\u2008​\u2009\u200a​\u2028\u2029​​\u202f\u205f​\u3000]

参考资料


2
很有可能问题出现在将字节解码为文本的过程中,而不是在您将其作为字符串获取之前。不过您还没有向我们展示这一点。 - Jon Skeet
如果你只是想清理一个文件,而不需要编程实现,那么你可以在Notepad++中完成。 - johnny 5
1
该符号是\p{S} Unicode类别类的一部分。只需尝试 Regex.Replace(str, @"\p{S}+", "")。如果它不起作用,则字符串中不存在该符号,并且问题就在那里。请注意,你的一些尝试(@"[^\S\r\n]+"@"\s+"(该字符不是空格)和"^ [\ S \ r \ n0-9A-Za-z ().:%-/ ] + $"(添加 \S 使其匹配所有非空格字符,在这里应使用逐字字符串文字))没有意义。修剪也没有意义,因为该字符不处于前导/尾随位置。 - Wiktor Stribiżew
请将您拥有的确切原始字符串粘贴到问题正文中。您写道:“所有空格都不是普通空格”“*”,但在我复制字符串后,我只看到常规空格(\x20)。 - Wiktor Stribiżew
2
如果不清楚的话,这些字节是字节顺序标记(BOM),是Unicode编码格式的一部分。以正确的Unicode读取字符串可能会解决此问题。或者,由于人们错误地修改文件,标记可能已被添加多次。无论哪种方式,要注意在不理解它的情况下删除它可能会导致未来的问题。 - Michael Dorgan
显示剩余12条评论
3个回答

4

定义一组ASCII字符,并替换不在该范围内的任何内容。


我们只想找到Unicode字符,因此我们将匹配Unicode字符并进行替换。

Regex.Replace("This is my te\uFFFDxt from csv file", @"[^\u0000-\u007F]+", " ")

以上模式将匹配除集合 [ ] 中范围为 \u0000-\u007F (ASCII 字符(超过 \u007F 的所有内容都是 Unicode))的 ^ 之外的任何内容,并用空格替换。

结果

This is my te xt from csv file

您可以根据需要调整提供的范围\u0000-\u007F,以扩展允许字符的范围,以满足您的需求。


@WiktorStribiżew 你用什么手机应用程序来查看SO? - ΩmegaMan

4

使用String.Replace:

使用简单的String.Replace()方法。

我假设您想要删除的字符仅限于您在问题中提到的�,并且您希望用普通空格替换它们。

string text = "imp�ortant";
string cleaned = text.Replace('\u00ef', ' ')
        .Replace('\u00bf', ' ')
        .Replace('\u00bd', ' ');
// Returns 'imp   ortant'

或者使用Regex.Replace:
string cleaned = Regex.Replace(text, "[\u00ef\u00bf\u00bd]", " ");
// Returns 'imp   ortant'

尝试一下: Dotnet Fiddle

这个不起作用。实际上,它是一个单字符 U+FFFD(十进制 65533)�。很奇怪的是,c# 输出的是 "�",我的十六进制编辑器从源代码中显示为 U+00B7。更多信息请参见:https://dev59.com/JXI_5IYBdhLWcg3wMf9_#1488920 - Tim

0
如果您只需要ASCII,则可以尝试以下内容:
var ascii = new ASCIIEncoding();
byte[] encodedBytes = ascii.GetBytes(text);
var cleaned = ascii.GetString(encodedBytes).Replace("?", " ");

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接