Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/319.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
寻找C#等价的scanf_C#_Scanf - Fatal编程技术网

寻找C#等价的scanf

寻找C#等价的scanf,c#,scanf,C#,Scanf,我过去常常用C语言编写代码,我发现scanf函数非常有用。 不幸的是,C#中没有等价物 我用它来解析半结构化文本文件 我发现了一个scanf实现的相互测试示例。不幸的是,它看起来既旧又不完整 有人知道一个scanfC#实现吗?或者至少可以作为反向的string.Format?文件是“半结构化”的,您不能结合使用ReadLine()和TryParse()方法,或者使用Regex类来解析数据吗?您可以直接从C运行时库使用scanf,但是,如果需要使用不同的参数来运行它,这可能会很困难。我建议您使用正

我过去常常用C语言编写代码,我发现
scanf
函数非常有用。 不幸的是,C#中没有等价物

我用它来解析半结构化文本文件

我发现了一个
scanf
实现的相互测试示例。不幸的是,它看起来既旧又不完整


有人知道一个
scanf
C#实现吗?或者至少可以作为反向的
string.Format

文件是“半结构化”的,您不能结合使用ReadLine()和TryParse()方法,或者使用Regex类来解析数据吗?

您可以直接从C运行时库使用scanf,但是,如果需要使用不同的参数来运行它,这可能会很困难。我建议您使用正则表达式来完成任务,或者在这里描述该任务,也许还有其他方法。

您可以使用System.IO.FileStream和System.IO.StreamReader,然后从那里进行解析。

我想您需要C#library函数进行解析或转换

// here's an example of getting the hex value from a command line 
// program.exe 0x00080000

static void Main(string[] args)
{
    int value = Convert.ToInt32(args[1].Substring(2), 16);
    Console.Out.WriteLine("Value is: " + value.ToString());
}

c#中缺少类似scanf的函数是有充分理由的。它很容易出错,而且不灵活。使用正则表达式更加灵活和强大


另一个好处是,如果您需要在代码的不同部分解析相同的内容,那么在整个代码中更容易重用。

如果正则表达式不适用于您,我刚刚发布了一个
sscanf()
替换.NET。代码可以在上查看和下载。

我发现了一个比使用C中的sscanf或其他人重写的部分更好的解决方案(没有冒犯)

看一看这篇文章,它解释了如何创建命名组以从带图案的字符串中提取所需的数据。注意文章中的小错误和下面更好的版本。(结肠不是该组的一部分)

使用系统;
使用System.Text.RegularExpressions;
公开课范例
{
公共静态void Main()
{
字符串url=”http://www.contoso.com:8080/letters/readme.html";
Regex r=new Regex(@“^(?\w+):/[^/]+?(?:\d+)?/”,RegexOptions.None,TimeSpan.frommilluses(150));
匹配m=r.Match(url);
如果(m.成功)
WriteLine(r.Match(url.Result(${proto}:${port}));
}
}
//该示例显示以下输出:
//http::8080

尽管这看起来有点粗糙,但它确实完成了任务:

// Create the stream reader
sr = new StreamReader("myFile.txt");

// Read it
srRec = sr.ReadLine();

// Replace multiple spaces with one space
String rec1 = srRec.Replace("          ", " ");
String rec2 = rec1.Replace("         ", " ");
String rec3 = rec2.Replace("        ", " ");
String rec4 = rec3.Replace("       ", " ");
String rec5 = rec4.Replace("      ", " ");
String rec6 = rec5.Replace("     ", " ");
String rec7 = rec6.Replace("    ", " ");
String rec8 = rec7.Replace("   ", " ");
String rec9 = rec8.Replace("  ", " ");

// Finally split the string into an array of strings with Split
String[] srVals = rec9.Split(' ');

然后可以将数组srVals用作记录中的单个变量。

尝试导入msvcrt.dll

using System.Runtime.InteropServices;

namespace Sample
{
    class Program
    {
        [DllImport("msvcrt.dll", CallingConvention = CallingConvention.Cdecl)]
        public static extern int printf(string format, __arglist);

        [DllImport("msvcrt.dll", CallingConvention = CallingConvention.Cdecl)]
        public static extern int scanf(string format, __arglist);

        static void Main()
        {
            int a, b;
            scanf("%d%d", __arglist(out a, out b));
            printf("The sum of %d and %d is %d.\n", __arglist(a, b, a + b));
        }
    }
}
在.NETFramework上运行良好。但在Mono上,它会显示错误消息:

Unhandled Exception:
System.InvalidProgramException: Invalid IL code in Sample.Program:Main (): IL_0009: call      0x0a000001


[ERROR] FATAL UNHANDLED EXCEPTION: System.InvalidProgramException: Invalid IL code in Sample.Program:Main (): IL_0009: call      0x0a000001
如果需要单声道兼容性,则需要避免使用
arglist

using System.Runtime.InteropServices;

namespace Sample
{
    class Program
    {
        [DllImport("msvcrt.dll", CallingConvention = CallingConvention.Cdecl)]
        public static extern int printf(string format, int a, int b, int c);

        [DllImport("msvcrt.dll", CallingConvention = CallingConvention.Cdecl)]
        public static extern int scanf(string format, out int a, out int b);

        static void Main()
        {
            int a, b;
            scanf("%d%d", out a, out b);
            printf("The sum of %d and %d is %d.\n", a, b, a + b);
        }
    }
}
其中参数的数量是固定的

编辑2018-5-24


arglist
在.NET核心上也不起作用。似乎不赞成调用C vararg函数。您应该使用.NET字符串API,例如
string.Format

当然可以:)但是,与regex相比,scanf非常方便。我很确定这是值得的。正则表达式并没有那么糟糕。下载其中一个免费工具(如Expresso)和正则表达式更易于创建和使用。就我个人而言,我讨厌scanf():正则表达式给了你更多的控制和灵活性,至少值得学习基础知识。我在Perl编程的日子里学会了正则表达式&我喜欢它们,所以我很高兴在.NET中找到正则表达式。。。有趣的是,这里没有人质疑regex和scanf的性能。是的,这是Mitch Wheat建议使用ReadLine的一个强制性条件。哦,我不知道如何直接使用C运行库。我宁愿避免使用正则表达式,而是坚持使用正则表达式。这是一种邪恶的黑客手段,你最好使用正则表达式组匹配。这相当于.net的sscanf,甚至更好。请看下面的帖子。@jurik:我想要求你支持你的陈述会太过分了吧?Regex很棒,如果你喜欢,你可以使用它。但在C#中实现scanf是一种“黑客”行为吗?那只是对你不喜欢的事情吹毛求疵。这并不意味着它是一个黑客。看在上帝的份上,对那些决定做一些与你喜欢做的不同的事情的人要有一点宽容。好吧,我可能在没有正当证据的情况下表现得有点强硬,但让我来解释一下。我在一段时间前发现了这个线程,在查看了代码之后,我不想在生产中使用它。不知怎的,如果.net平台想要使用scanf,它会将其合并。所以我进一步研究,找到了我需要的例子。它的功能与sscanf完全相同,但没有自定义代码。对不起,我不是有意冒犯你或你的解决方案。实际上我非常喜欢黑客。有时它是必要的。@jurik:RegEx做的更多,所以我当然能理解人们喜欢它。我为C#编写scanf的主要原因是为了让开发人员更容易移植C代码,也让熟悉scanf语法但不熟悉regex的人更容易移植C代码。不错!如果至少涵盖了基本知识,那么移植就容易多了。值得注意的是,这个示例实际上并没有给出预期的输出。当我测试它时,它会产生
http::8080
。你完全正确,但这毫无意义。结肠在匹配的组之外,因此不应接受。我假设proto是http,端口是8080,没有冒号。这就是我编辑原始示例的原因。您有十行代码可以替换为一行
var srVals=srRec.Split(new char[]{'''},StringSplitOptions.RemoveEmptyEntries)以获得更可预测的行为。但除此之外,这并不能真正回答问题。
using System.Runtime.InteropServices;

namespace Sample
{
    class Program
    {
        [DllImport("msvcrt.dll", CallingConvention = CallingConvention.Cdecl)]
        public static extern int printf(string format, int a, int b, int c);

        [DllImport("msvcrt.dll", CallingConvention = CallingConvention.Cdecl)]
        public static extern int scanf(string format, out int a, out int b);

        static void Main()
        {
            int a, b;
            scanf("%d%d", out a, out b);
            printf("The sum of %d and %d is %d.\n", a, b, a + b);
        }
    }
}