0

情報を抽出したい ~7MB のテキスト ファイルがあり、次のような形式のインスタンスが多数含まれています。

            "name": "Riki's Dagger",
            "defindex": 0,
            "item_class": "dota_item_wearable",
            "item_type_name": "#DOTA_WearableType_Daggers",
            "item_name": "#DOTA_Item_Rikis_Dagger",
            "proper_name": false,
            "item_quality": 0,
            "image_inventory": null,
            "min_ilevel": 1,
            "max_ilevel": 1,
            "image_url": "",
            "image_url_large": "",

名前と defindex を抽出し、このインスタンスにキーワードが含まれているか含まれていないかを確認し、後で使用できるように新しいテキスト ファイルに配置します。私の計画は、"name" の各インスタンス (引用符付き) をファイルで検索し、"name" の次のインスタンスの前のすべての内容を current という変数に設定することでした。次に、現在の文字列で必要な情報を検索します。それが最善の方法ですか、どうすればよいですか?正規表現を使用する必要がありますか、それともファイルが大きすぎますか? いくつかの方向性をいただければ幸いです。

これは私がこれまでに持っているものです:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data;
using System.IO;

namespace ConsoleApplication1
{
    class Test
    {
        static void Main(string[] args)
            {
            string ingameschemaFilePath = @"C:\Users\Andrew\Documents\GitHub\SteamBot\Bin\Debug\ingameschema.txt";
            string dota2schemaFilePath = @"C:\Users\Andrew\Documents\GitHub\SteamBot\Bin\Debug\dota2schema.txt";
            string schemaFilePath = @"C:\Users\Andrew\Documents\GitHub\SteamBot\Bin\Debug\schema.txt";

            string[] ingameschema = File.ReadAllLines(ingameschemaFilePath);
            string[] dota2schema = File.ReadAllLines(dota2schemaFilePath);
            string[] current = null;
            string[] name = null;
            string[] defindex = null;
            string[] rarity = null;

            using (TextWriter textWriter = new StreamWriter(schemaFilePath))
            {
                foreach (//search for "name"->"name" segment here)
                {
                    //    if current.Contains("dota_item_wearable") == false, current.Contains("announcer", "courier", "ward", "egg", "costume", "HUD", "smeevil", "taunt", "bait", "lure", "bundle" ) == true, 
                    //          break
                    }
                }
            System.Console.WriteLine("Press any key to exit.");
            System.Console.ReadKey();
    }
    }
}
4

2 に答える 2

0

StreamReaderテキストファイルから1行ずつ読み取り、その行で目的の情報を見つけるために使用する必要があると思います。

読み取りが完了するまでファイルの一部を保存している場合にのみ問題があります。その後、メモリの問題が発生する可能性があります(ただし、リストと辞書がメモリ不足になる前に取得できるサイズに驚かれることでしょう) )

あなたがする必要があるのは、処理されたデータをできるだけ早く保存し、それをメモリに保持しない (またはできるだけメモリに保持しない) ことです。

于 2013-08-16T13:24:03.980 に答える
0

考えられるアプローチの 1 つは、ソースをある種の辞書ベースのコレクションに入れ、そのアイテムに関心のあるキーでアドレス指定できるようにすることです。

    static void Main(string[] args)
    {
        string sourcefile = @"C:\test\source.txt";
        string outputfile = @"C:\test\output.txt";

        string[] source = File.ReadAllLines(sourcefile);

        // The list would represent the collection of all the items 
        List<NameValueCollection> list = new List<NameValueCollection>();

        // Each nvc would represent the collection of attributes for that item
        NameValueCollection nvc = null;

        foreach (string s in source)
        {
            //Split your string into its key and value
            string[] nv = s.Split(':');

            //If the key is name you have finished your previous item, and will it to the list and start a new one
            if (nv[0] == "name")
            {
                if (nvc != null)
                    list.Add(nvc);

                nvc = new NameValueCollection();
            }
            // Add your attribute and value to the items attribute collection
            nvc.Add(nv[0], nv[1]);
        } 
    }

7MB は少し大きいですが、今日のメモリでは問題ないはずです。それが問題になる場合は、代わりに Stream オブジェクトから ReadLine を使用することを検討してください。これにより、各行が一度に 1 つずつメモリに読み込まれます。

これがまったく役立つかどうか教えてください。

于 2013-08-16T13:41:41.587 に答える