【先着1,000名様!】1,000円分をプレゼント!

C#初心者です。

以下のように、カンマ区切りのcsvファイルの特定の列を入れ替えて保存するアプリを作ろうとしています。
■変更前
りんご,赤,1,
みかん,オレンジ,2
メロン,黄緑,3

■変更後
1,赤,りんご,
2,オレンジ,みかん,
3,黄緑,メロン,

以下のような概略フローを考えてみたのですが、
(3)の処理を実行する場合、どのような実装すれば良いか分かりません。

■概略フロー
(1)1行ずつTextFieldParserで、string配列に読み込む
(2)任意の列の値を左から順番を指定して並べ替える
 No.3の列を左から1列目に指定⇒No.3の列を左から3列目に指定
(3)並べ替えた配列をカンマ区切りで再結合する

どなたかご教示いただけると助かります。

このQ&Aに関連する最新のQ&A

A 回答 (3件)

TextFieldParser の流れなら ReadFields() で 1行分を列ごとに分けて読み込むわけだから、あとは任意の順番で文字列連結すればいいんじゃない?



string[] rowData = parser.ReadFields();
ConsoleWriteLine(rowData[2] + "," + rowData[1] + "," + rowData[0]);
とか
    • good
    • 0
この回答へのお礼

ご教示ありがとうございます。

ConsoleWriteLineなら単純に文字の間にカンマを入れるだけで、新しい文字列が作れるんですね。
他にもJoinメソッドというものも用意されているようですね。
C#の利便性を活用できるよう、勉強していきたいと思います。

お礼日時:2012/03/24 00:40

テキストファイルの書き込み方法はいろいろありますが、


基本的に一行ずつ書き込みます。

string[] splittedResult = txtParser.ReadFields();
で取り込んだものを任意の順にカンマ区切りにして
一行分のStringをWriteLineに渡します。

Encoding sjisEnc = Encoding.GetEncoding("Shift_JIS");
StreamWriter writer = new StreamWriter(@"C:\Test.txt", true, sjisEnc);
writer.WriteLine("テスト書き込みです。");
writer.Close();
    • good
    • 0
この回答へのお礼

ご教示ありがとうございます。

StreamWriterクラスという便利なものがあるのですね。
C#初心者なのですが、その便利さをほんの少し知ることができました。

お礼日時:2012/03/24 00:30

まぁあんまり頭で考えず力技で実装すればいいんじゃないでしょうか。



実際にコードを書いて、どう動くか試行錯誤すると見えてくるものもあると思います。
    • good
    • 0

このQ&Aに関連する人気のQ&A

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!

このQ&Aを見た人はこんなQ&Aも見ています

このQ&Aを見た人が検索しているワード

このQ&Aと関連する良く見られている質問

Qc#で(",")区切りのcsvファイルから読み込みを行うには?

駆け出しの初心者です。
以前c言語を少々勉強していてcsvファイルの読み込み、書き出しを練習していたのですが、最近c#を使うようになり、その便利さに圧倒されております。

今回c#で読み込みたいcsvファイルは以下のようになっております
"abc","123","あいうえお"

ただのカンマ区切りであれば読み込みは簡単ですが、
上記のようにダブルクオーテーションでそれぞれの文字列が囲まれている場合に文字列だけを読み込み、配列に代入していくのに何かスムーズな方法はありませんでしょうか?


ちなみに現在単純にカンマ区切りのcsvファイルを読み込むコードを
書いた所ですので、載せておきます
これをいじってスムーズにいければうれしいのですが、いかがでしょうか?

private void LoadData()
{
string path = "Data.csv";
string delimStr = ",";//区切り文字
char[] delimiter = delimStr.ToCharArray();
string[] strData;//分解後の文字用変数
string strLine;//1行分のデータ
Boolean fileExists = System.IO.File.Exists(path);
if (fileExists)
{
System.IO.StreamReader sr = new System.IO.StreamReader(
path,
System.Text.Encoding.Default);
while (sr.Peek() >= 0)
{
strLine = sr.ReadLine();
strData = strLine.Split(delimiter);
DataSet.DataTable.AddDataTableRow(
DateTime.Parse(strData[0]),
strData[1],
   strData[2],
int.Parse(strData[3]),
strData[4]);
}

sr.Close();
}


}


いつも丁寧な回答で協力してくれる皆様には心から感謝しております。
どうぞよろしくお願いします。

駆け出しの初心者です。
以前c言語を少々勉強していてcsvファイルの読み込み、書き出しを練習していたのですが、最近c#を使うようになり、その便利さに圧倒されております。

今回c#で読み込みたいcsvファイルは以下のようになっております
"abc","123","あいうえお"

ただのカンマ区切りであれば読み込みは簡単ですが、
上記のようにダブルクオーテーションでそれぞれの文字列が囲まれている場合に文字列だけを読み込み、配列に代入していくのに何かスムーズな方法はありませんでしょうか?


ちなみに...続きを読む

Aベストアンサー

こう応用するとよいです。
以下に全コードを載せておきますが、ポイントはこの一行です。
strData = strLine.Split(delimiter);

strData = CsvToArrayList1(strLine)[0];


private void LoadData() {
string path = "Data.csv";
string[] strData;//分解後の文字用変数
string strLine;//1行分のデータ
Boolean fileExists = System.IO.File.Exists(path);
if(fileExists) {
System.IO.StreamReader sr = new System.IO.StreamReader(path,System.Text.Encoding.Default);
while(sr.Peek() >= 0) {
strLine = sr.ReadLine();
strData = CsvToArrayList1(strLine)[0];//変更点
DataSet.DataTable.AddDataTableRow(
DateTime.Parse(strData[0]),
strData[1],
strData[2],
int.Parse(strData[3]),
strData[4]);
}

sr.Close();
}
}


//参照先<http://dobon.net/vb/dotnet/file/readcsvfile.html>
//参照先だとArrayListを返し値にしていますが使いづらいので、List<string[]>に変更しています。
public static System.Collections.Generic.List<string[]> CsvToArrayList1(string csvText) {
System.Collections.Generic.List<string[]> csvRecords =
new System.Collections.Generic.List<string[]>();

//前後の改行を削除しておく
csvText = csvText.Trim(new char[] { '\r', '\n' });

//一行取り出すための正規表現
System.Text.RegularExpressions.Regex regLine =
new System.Text.RegularExpressions.Regex(
"^.*(?:\\n|$)",
System.Text.RegularExpressions.RegexOptions.Multiline);

//1行のCSVから各フィールドを取得するための正規表現
System.Text.RegularExpressions.Regex regCsv =
new System.Text.RegularExpressions.Regex(
"\\s*(\"(?:[^\"]|\"\")*\"|[^,]*)\\s*,",
System.Text.RegularExpressions.RegexOptions.None);

System.Text.RegularExpressions.Match mLine = regLine.Match(csvText);
while(mLine.Success) {
//一行取り出す
string line = mLine.Value;
//改行記号が"で囲まれているか調べる
while((CountString(line, "\"") % 2) == 1) {
mLine = mLine.NextMatch();
if(!mLine.Success) {
throw new ApplicationException("不正なCSV");
}
line += mLine.Value;
}
//行の最後の改行記号を削除
line = line.TrimEnd(new char[] { '\r', '\n' });
//最後に「,」をつける
line += ",";

//1つの行からフィールドを取り出す
System.Collections.Generic.List<string> csvFields =
new System.Collections.Generic.List<string>();
System.Text.RegularExpressions.Match m = regCsv.Match(line);
while(m.Success) {
string field = m.Groups[1].Value;
//前後の空白を削除
field = field.Trim();
//"で囲まれている時
if(field.StartsWith("\"") && field.EndsWith("\"")) {
//前後の"を取る
field = field.Substring(1, field.Length - 2);
//「""」を「"」にする
field = field.Replace("\"\"", "\"");
}
csvFields.Add(field);
m = m.NextMatch();
}

csvFields.TrimExcess();
csvRecords.Add(csvFields.ToArray());

mLine = mLine.NextMatch();
}

csvRecords.TrimExcess();
return csvRecords;
}

/// <summary>
/// 指定された文字列内にある文字列が幾つあるか数える
/// </summary>
/// <param name="strInput">strFindが幾つあるか数える文字列</param>
/// <param name="strFind">数える文字列</param>
/// <returns>strInput内にstrFindが幾つあったか</returns>
public static int CountString(string strInput, string strFind) {
int foundCount = 0;
int sPos = strInput.IndexOf(strFind);
while(sPos > -1) {
foundCount++;
sPos = strInput.IndexOf(strFind, sPos + 1);
}

return foundCount;
}

こう応用するとよいです。
以下に全コードを載せておきますが、ポイントはこの一行です。
strData = strLine.Split(delimiter);

strData = CsvToArrayList1(strLine)[0];


private void LoadData() {
string path = "Data.csv";
string[] strData;//分解後の文字用変数
string strLine;//1行分のデータ
Boolean fileExists = System.IO.File.Exists(path);
if(fileExists) {
System.IO.StreamReader sr = new System.IO.StreamReader(path,System.Text.Encoding.Default);
while(sr.Peek() >= 0...続きを読む

Qc#でcsvから指定の1行だけを読み込む方法

以前c言語で同じような質問をして、とても有益な回答を頂きましたが、
今回c#でのコードの書き方をご教示いただければと思い、再度質問致します。

例えば以下のようなcsvファイルがあったとします。

ab1,ef2,ab3,af4,ab5
bb1,bf2,bb3,bf4
cb1,cf2,cb3,cf4,cb5
zb1,zf2,zb3,zf4,zb5


プログラムに"cb3"という文字列を探させて、その文字列を含む一行
"cb1,cf2,cb3,cf4,cb5"のみを読み込む方法を探しております。


現時点では以下のコードにてcsvファイルを丸々読み込んでおります。

private void LoadData()//csvファイルを読み込む
{
string path = "abc.csv";
string delimStr = ",";//区切り文字
char[] delimiter = delimStr.ToCharArray();//区切り文字をまとめる
string[] strData;//分解後の変数
string strLine; //1行分のデータ

Boolean fileExists = System.IO.File.Exists(path);
if (fileExists)
{
System.IO.StreamReader sr = new System.IO.StreamReader(
path,
System.Text.Encoding.Default
);

while (sr.Peek() >= 0)
{
strLine = sr.ReadLine();
strData = CsvToArrayList1(strLine)[0];
abc.abctable.AddabctableRow
(
strData[0],
int.Parse(strData[1])
);
} sr.Close();



}



c言語の時はstrstrで特定の文字を含む1行のみを取得できたのですが、
c#ではもっと良い方法があるのではと考えております、
お時間がありましたら是非教えてください。

皆様の丁寧な回答にいつも感謝しております。

以前c言語で同じような質問をして、とても有益な回答を頂きましたが、
今回c#でのコードの書き方をご教示いただければと思い、再度質問致します。

例えば以下のようなcsvファイルがあったとします。

ab1,ef2,ab3,af4,ab5
bb1,bf2,bb3,bf4
cb1,cf2,cb3,cf4,cb5
zb1,zf2,zb3,zf4,zb5


プログラムに"cb3"という文字列を探させて、その文字列を含む一行
"cb1,cf2,cb3,cf4,cb5"のみを読み込む方法を探しております。


現時点では以下のコードにてcsvファイルを丸々読み込んでおります。

private...続きを読む

Aベストアンサー

http://homepage3.nifty.com/midori_no_bike/CS/

今回の件では必要ないかもしれませんが、C#では正規表現で検索できるのが興味深いと思います。

QC#にて別クラスの関数を使いたい

C#にて、別クラスの関数を使用する方法を教えてほしいです。

下記のような、構造体を受け取るメソッドを作りました。

*****************************
private struct MyPoint
{
public int x;
public int y;
}

private void proc1(MyPoint pt)
{
MessageBox.Show("座標:" ; pt.x + "," + pt.y + "実行結果");
}

private void button1_Click(object sender ,System.EventArgs e)
{

MyPoint pt;
pt.x = 10;
pt.y = 20;
proc(pt);
}
*****************************

別のフォームのクラスから、proc1を呼び出したいのですが、やり方がわかりません。
どうか、教えてください。

Aベストアンサー

同じ定義をしたとしても別の名前空間に書いた構造体は同一とはみなされません。

呼び出し先クラスでの構造体を private では無く、public で宣言して下さい。

呼び出し元では、

MyClass.MyPoint pt;

のようにして実体を作ります。

QC# 行列の入替

今,マトリックスを作成しこのマトリックスの配列を行列入替ようとしています.

ネットで調べた結果下記の方法が見つかりましたが,使用方法が良く解りません.

http://msdn.microsoft.com/ja-jp/library/bb199546(v=xnagamestudio.40)

現状,元のマトリックスはcsv.matrix 入替後のマトリックスはNewmatrixという名前のマトリックスに

格納したいと考えております.

どの様にすれば良いか本当にご教授お願いたします.

Aベストアンサー

プログラムの先頭に
using Microsoft.Xna.Framework;
を追加しておいて、
Matrix.Transpose(csv.matrix, Newmatrix);
とすればよいのではありませんか。

QC#でCSVファイルを逐一更新したい

C#のプログラムで
データをCSVファイルに蓄積するプログラムを作っています。

やり方としては最初にCSVファイルを指定し
ボタンを押すたびに、データを追加するように作りました。
以下抜粋

//CSVファイル指定
csvfile = new System.IO.StreamWriter(csvPath, true, encording);



//データの書き込み
csvfile.Write(data);
csvfile.Write(",");



//CSVファイルクローズ
csvfile.Close();

このプログラムを動作させた所
「csvfile.Close();」の時点で、実際にcsvにデータが書き込まれました。
データの書き込みのたびにCSVファイルが更新されるのが理想なのですが、
その方法としては逐一クローズするしか方法はないのでしょうか?

何らかの方法で逐一更新出来たり、
もしくは異なるCSVへの書き込み方法があれば、教えていただけないでしょうか?

Aベストアンサー

http://msdn.microsoft.com/ja-jp/library/system.io.streamwriter.flush%28v=vs.80%29.aspx

できるのはこれくらい。
StreamWriter調べればわかったことだと思うけど。

QCSVファイルの特定行の削除

CSVファイルの特定行を削除するということは可能なのでしょうか?
可能であれば教えて頂けないでしょうか?
お願いします。

Aベストアンサー

書き換えるというよりは、
その行を除いて別のファイルへコピーするという方法が一般的ですね。

例:AをCSVファイルだとすると、
1.Bという空のファイルを生成する。
2.Aから1行ずつ読みBへ1行ずつコピーする。
 ⇒削除したい行はコピーしない。
3.Aの最後行まで達したらAを削除し、BをAにリネームする。

こんな感じです。

Qフルパスから最後のディレクトリ名を取得したい。

vb.netなのですが、例えば
c:\aaa\bbb\ccc\ddd\eee\fff.exe
というフルパスがあったとして、
eeeというディレクトリ名を取得したいのですが、
何か良い方法はないでしょうか。
それぞれのディレクトリ名の文字数や階層数は
決まっていないのですが、オススメの方法が
ありましたら、教えて頂けると助かります。

Aベストアンサー

MessageBox.Show(IO.Path.GetFileName(IO.Path.GetDirectoryName(myPath)))

IO.Path の GetDirectoryName でフォルダのフルパスを取得して、さらに IO.Path の GetFileName で最終フォルダ(またはファイル)の名前を取得。

QC#「オブジェクト参照が必要です」(初心者)

Visual C# 2008を学習中なんですが、とりあえず何か作ってみようと思って、パラパラマンガに挑戦してみました。
Form1にpictureBox1を作り、waitを入れてイメージを書き換えるという単純なものです。
ところが実行しようと思ったら、「静的でないフィールド、メソッド、またはプロパティ’WindowsFormApplication1.Form1.pictureBox1’でオブジェクト参照が必要です」というエラーが出ます。その際のフォーカスは、main()内の
Form1.pictureBox1.image = Image.FromFile("motion1.png");
”Form1.pictureBox1”に当てられています。

何が原因と考えられるでしょうか。
もし情報不足であればご指摘いただくか、あるいはこの目的においてやらなければいけないこと、を大雑把に教えていただくだけでも幸いです。
よろしくお願いします。

Aベストアンサー

main()内に記述されているとのことですので、たぶん、
Form1.pictureBox1.Image=Image.FromFile("motion1.png");
Application.Run(new Form1());
と書いているのではないでしょうか?

連載 改訂版 C#入門 第3章 クラスとインスタンス
http://www.atmarkit.co.jp/fdotnet/csharp_abc2/csabc2_003/cs2_003_01.html#cs0302

ここであるように、オブジェクト指向にはクラスとインスタンスという概念があります。
今のコードでは、Form1クラスを操作しようとしているのでそのようなエラーが出ます。

具体的な解決方法としては、PictureBoxに初期画像を設定する処理をForm1のコンストラクタでやるのがいいと思います。
その際、redfox63さんがおっしゃられるように
this.pictureBox1
と記述することが必要です。(thisは自分自身のインスタンスを指します)

後は、Windowsフォームで一定間隔での処理をするための「Timerコンポーネント」について調べてみたらいいと思います。

タイマにより一定時間間隔で処理を行うには?(Windowsタイマ編)
http://www.atmarkit.co.jp/fdotnet/dotnettips/372formstimer/formstimer.html

MSDNライブラリ Timerクラス
http://msdn.microsoft.com/ja-jp/library/system.windows.forms.timer.aspx

参考URL:http://www.atmarkit.co.jp/fdotnet/csharp_abc2/index/

main()内に記述されているとのことですので、たぶん、
Form1.pictureBox1.Image=Image.FromFile("motion1.png");
Application.Run(new Form1());
と書いているのではないでしょうか?

連載 改訂版 C#入門 第3章 クラスとインスタンス
http://www.atmarkit.co.jp/fdotnet/csharp_abc2/csabc2_003/cs2_003_01.html#cs0302

ここであるように、オブジェクト指向にはクラスとインスタンスという概念があります。
今のコードでは、Form1クラスを操作しようとしているのでそのようなエラーが出ます。

具...続きを読む

QC#でプログラミング。 csvファイルへの書き込みについて

フォームに貼ったtextboxやlistboxの内容をボタンを押すことで、
csvファイルで書き出したいと考えています。

C#は初心者なので調べてみてもよくわからずにいます。

どのようにしたらよいのでしょうか??
また、いいサイトなどをご存知の方がいましたら教えてください。

Aベストアンサー

http://dobon.net/vb/dotnet/file/writecsvfile.html
とりあえず、見つかりました。

csvは数値のみなどの表を保存するのには向いていますが、フォームで入力された値などを保存するには不向きで、app.configなどを使う方がよろしいかと…あくまでも私見ですが。

QCSVファイルの中で、「 , 」カンマを使いたい

「 , 」で区切られたCSVファイルの中で、「 , 」カンマを使いたいのですが、可能でしょうか?

具体的には「これは1,500円でした。」というように、CSVファイルに収められた文章内で出てくる半角の数字(お金)の区切りに使いたいのです。
全角では代用したくないのですが、CSVファイルでデータを受け渡しする際に、困っています。

例えば、特殊文字などで対応可能でしょうか?

Aベストアンサー

受け渡しに使うと言うことは相手方のアプリケーションのことも考えなければいけないのですが・・・とりあえず対応が簡単そうな方法を。

1.各セルを""で囲む。(もちろんデータにダブルクォートがある場合はカンマと同様に困ります。
2.カンマで区切らずにタブで区切る。(比較的使われない文字ですが、やはりデータ中にタブがあるとカンマと同様です)

難しいけれど完璧に対応するためには、データ中の区切り文字は特殊な文字列に変更し、受け取り側のアプリケーションではその特殊な文字列をデータ中の区切り文字として扱うという方法が使われます。
例えば、データ中のカンマは\,にするとか。

データ作成側、受け取り側でそれぞれどこまで対応できるのか分かるともっと簡単かつ具体的な方法を回答できるかも知れません。


このQ&Aを見た人がよく見るQ&A

人気Q&Aランキング