给出C#/ .NET Core 2.1中的以下代码
class Program
{
static void Main(string[] args)
{
var totalAmountSeconds = 0;
using (var reader = XmlReader.Create(@"C:\Users\kevin\Desktop\temp\XML.xml"))
{
var stopWatch = new Stopwatch();
var elementCounter = 0;
stopWatch.Start();
foreach (var element in XmlReaderUtils.EnumerateAxis(reader, new[] { "Node" }))
{
elementCounter += 1;
}
stopWatch.Stop();
totalAmountSeconds += stopWatch.Elapsed.Seconds;
Console.WriteLine("Total '<Node />' elements: " + elementCounter);
}
using (var reader = XmlReader.Create(@"XML.xml"))
{
var stopWatch = new Stopwatch();
var elementCounter = 0;
stopWatch.Start();
foreach (var element in XmlReaderUtils.EnumerateAxis(reader, new[] { "ArticleGroup" }))
{
elementCounter += 1;
}
stopWatch.Stop();
totalAmountSeconds += stopWatch.Elapsed.Seconds;
Console.WriteLine("Total '<ArticleGroup />' elements: " + elementCounter);
}
Console.WriteLine("Total amount of required seconds: " + totalAmountSeconds);
}
}
public static class XmlReaderUtils
{
public static IEnumerable<XElement> EnumerateAxis(XmlReader reader,
string[] elements)
{
reader.MoveToContent();
while (reader.Read())
{
switch (reader.NodeType)
{
case XmlNodeType.Element:
if (!elements.Contains(reader.Name)) continue;
yield return XNode.ReadFrom(reader) as XElement;
break;
}
}
}
}
我确实认为GoLang中此代码的确切副本应为以下内容:
package main
import (
"encoding/xml"
"fmt"
"os"
"time"
)
func main() {
start := time.Now()
xmlFile, _ := os.Open("XML.xml")
defer xmlFile.Close()
decoder := xml.NewDecoder(xmlFile)
amountOfElements := 0
for {
t, _ := decoder.Token()
if t == nil {
break
}
// Inspect the type of the token just read.
switch se := t.(type) {
case xml.StartElement:
if se.Name.Local == "Node" {
amountOfElements++
}
}
}
fmt.Printf("Total '<Node />' elements: %v\n", amountOfElements)
xmlFile, _ = os.Open("XML.xml")
defer xmlFile.Close()
decoder = xml.NewDecoder(xmlFile)
amountOfElements = 0
for {
t, _ := decoder.Token()
if t == nil {
break
}
// Inspect the type of the token just read.
switch se := t.(type) {
case xml.StartElement:
if se.Name.Local == "ArticleGroup" {
amountOfElements++
}
}
}
fmt.Printf("Total '<ArticleGroup />' elements: %v\n", amountOfElements)
fmt.Printf("Total elapsed time: %v", time.Since(start))
}
.NET中的代码执行需要1分钟,而在GoLang中则需要2分钟。
.NET版本是使用Release配置构建的,请转到GoLang go build
。
我期望GoLang更快,但事实证明它会慢吗? 这是正常现象还是我错过了什么?
答案 0 :(得分:0)
xml.NewDecoder
包含两种从文件读取XML令牌的方法-Token()和RawToken()。
Tocken()
包含一些其他有关StartElement和EndElement匹配的检查,并将名称空间前缀转换为它们相应的URL。
如果确实注意到这些功能,请尝试RawToken()
。
P.S。在C#中,您读取2个不同的文件,在GO中,您读取相同的文件两次。难道第二个文件在C#示例中更小/更简单?