file I/O in xna windows phone.... reading and writing text data - c#

i wants to increment the score of player and check the highscore, so that i am storing score in text file.i am trying below code but it is throwing exception.
Exception : Value does not fall within the expected range.
public void storage()
{
var appstorage = IsolatedStorageFile.GetUserStoreForApplication();
String filename = "store.txt";
using (var file = appstorage.OpenFile(filename, FileMode.OpenOrCreate,FileAccess.ReadWrite))
{
using (var writer = new StreamWriter(file))
{
writer.Write(score);
}
using(var reader=new StreamReader(file))
{
playerscore =reader.ReadLine();
}
}
}

I am really not sure about windows phone support but in windows I would do it something like this
using (var file = File.Open(filename, FileMode.OpenOrCreate, FileAccess.ReadWrite))
{
using (var writer = new BinaryWriter(file))
{
writer.Write(score);
}
using (var reader = new BinaryReader(file))
{
playerscore = reader.ReadInt32();
}
}
Of course if you can only read an write text this would be the solution
using (var file = File.Open(filename, FileMode.OpenOrCreate,` FileAccess.ReadWrite))
{
using (var writer = new StreamWriter(file))
{
writer.WriteLine(score.ToString());
}
using (var reader = new StreamReader(file))
{
playerscore = int.Parse(reader.ReadLine());
}
}

Related

C# ZipArchive: zip file not created

I tried below code to first convert my bytes to compressed bytes and try to create a zip file, but file is not generated. Could someone please suggest!
byte[] result;
var X = 86251;
byte[] compressedBytes;
using (FileStream SourceStream = File.Open(filename, FileMode.Open))
{
SourceStream.Seek(0, SeekOrigin.Begin);
result = new byte[X];
await SourceStream.ReadAsync(result, 0, X);
}
string fileName = "Export_" + DateTime.Now.ToString("yyyyMMddhhmmss") + ".zip";
using (var outStream = new MemoryStream())
{
using (var archive = new ZipArchive(outStream, ZipArchiveMode.Create, true))
{
var fileInArchive = archive.CreateEntry(fileName, CompressionLevel.Optimal);
using (var entryStream = fileInArchive.Open())
using (var fileToCompressStream = new MemoryStream(result))
{
fileToCompressStream.CopyTo(entryStream);
}
}
compressedBytes = outStream.ToArray();
}
You're not creating an actual file anywhere. You're just writing to a memory stream. Change it to write to a file.
using (var outStream = new File.Create(fileName))
{
using (var archive = new ZipArchive(outStream, ZipArchiveMode.Create, true))
{
var fileInArchive = archive.CreateEntry(filename, CompressionLevel.Optimal);
using (var entryStream = fileInArchive.Open())
using (var fileToCompressStream = new MemoryStream(result))
{
fileToCompressStream.CopyTo(entryStream);
}
}
}

Move position in FileStream (C#)

I have a txt file like this
#header1
#header2
#header3
....
#headerN
ID Value Pvalue
a 0.1 0.002
b 0.2 0.002
...
My code will try to parse
FileStream fs = new FileStream(file, FileMode.Open, FileMode.Read);
......
Table t = Table.Load(fs);
what I want is to make the start position of the Stream right before "ID", so I can feed the stream to the code and make a new table. But I am not sure what is the correct way to do it.
Thanks in advance
Ideally, you should convert Table.Load to take an IEnumerable<string> or at least a StreamReader, not a raw Stream.
If this is not an option, you can read the whole file into memory, skip its header, and write the result into MemoryStream:
MemoryStream stream = new MemoryStream();
using (var writer = new StreamWriter(stream, Encoding.UTF8);
foreach (var line in File.ReadLines(fileName).SkipWhile(s => s.StartsWith("#"))) {
writer.WriteLine(line);
}
}
stream.Position = 0;
Table t = Table.Load(stream);
Try this code
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
namespace ConsoleApplication57
{
class Program
{
const string file = "";
static void Main(string[] args)
{
FileStream fs = new FileStream(file, FileMode.Open, FileAccess.Read);
StreamReader reader = new StreamReader(fs);
string inputline = "";
State state = State.FIND_HEADER;
while((inputline = reader.ReadLine()) != null)
{
switch (state)
{
case State.FIND_HEADER:
if (inputline.StartsWith("#header"))
{
state = State.READ_TABLE;
}
break;
case State.READ_TABLE:
Table t = Table.Load(fs);
break;
}
}
}
enum State
{
FIND_HEADER,
READ_TABLE
}
}
}

Create and write to a text file inmemory and convert to byte array in one go

How can I create a .csv file implicitly/automatically by using the correct method, add text to that file existing in memory and then convert to in memory data to a byte array?
string path = #"C:\test.txt";
File.WriteAllLines(path, GetLines());
byte[] bytes = System.IO.File.ReadAllBytes(path);
With that approach I create a file always (good), write into it (good) then close it (bad) then open the file again from a path and read it from the hard disc (bad)
How can I improve that?
UPDATE
One nearly good approach would be:
using (var fs = new FileStream(#"C:\test.csv", FileMode.Create, FileAccess.ReadWrite))
{
using (var memoryStream = new MemoryStream())
{
fs.CopyTo(memoryStream );
return memoryStream .ToArray();
}
}
but I am not able to write text into that filestream... just bytes...
UPDATE 2
using (var fs = File.Create(#"C:\temp\test.csv"))
{
using (var sw = new StreamWriter(fs, Encoding.Default))
{
using (var ms = new MemoryStream())
{
String message = "Message is the correct ääüö Pi(\u03a0), and Sigma (\u03a3).";
sw.Write(message);
sw.Flush();
fs.CopyTo(ms);
return ms.ToArray();
}
}
}
The string message is not persisted to the test.csv file. Anyone knows why?
Write text into Memory Stream.
byte[] bytes = null;
using (var ms = new MemoryStream())
{
using(TextWriter tw = new StreamWriter(ms)){
tw.Write("blabla");
tw.Flush();
ms.Position = 0;
bytes = ms.ToArray();
}
}
UPDATE
Use file stream Directly and write to File
using (var fs = new FileStream(#"C:\ed\test.csv", FileMode.Create, FileAccess.ReadWrite))
{
using (TextWriter tw = new StreamWriter(fs))
{
tw.Write("blabla");
tw.Flush();
}
}
You can get a byte array from a string using encoding:
Encoding.ASCII.GetBytes(aString);
Or
Encoding.UTF8.GetBytes(aString);
But I don't know why you would want a csv as bytes. You could load the entire file to a string, add to it and then save it:
string content;
using (var reader = new StreamReader(filename))
{
content = reader.ReadToEnd();
}
content += "x,y,z";
using (var writer = new StreamWriter(filename))
{
writer.Write(content);
}
Update: Create a csv in memory and pass back as bytes:
var stringBuilder = new StringBuilder();
foreach(var line in GetLines())
{
stringBuilder.AppendLine(line);
}
return Encoding.ASCII.GetBytes(stringBuilder.ToString());

C# ZipArchive losing data

I'm trying to copy the contents of one Excel file to another Excel file while replacing a string inside of the file on the copy. It's working for the most part, but the file is losing 27 kb of data. Any suggestions?
public void ReplaceString(string what, string with, string path) {
List < string > doneContents = new List < string > ();
List < string > doneNames = new List < string > ();
using(ZipArchive archive = ZipFile.Open(_path, ZipArchiveMode.Read)) {
int count = archive.Entries.Count;
for (int i = 0; i < count; i++) {
ZipArchiveEntry entry = archive.Entries[i];
using(var entryStream = entry.Open())
using(StreamReader reader = new StreamReader(entryStream)) {
string txt = reader.ReadToEnd();
if (txt.Contains(what)) {
txt = txt.Replace(what, with);
}
doneContents.Add(txt);
string name = entry.FullName;
doneNames.Add(name);
}
}
}
using(MemoryStream zipStream = new MemoryStream()) {
using(ZipArchive newArchive = new ZipArchive(zipStream, ZipArchiveMode.Create, true, Encoding.UTF8)) {
for (int i = 0; i < doneContents.Count; i++) {
int spot = i;
ZipArchiveEntry entry = newArchive.CreateEntry(doneNames[spot]);
using(var entryStream = entry.Open())
using(var sw = new StreamWriter(entryStream)) {
sw.Write(doneContents[spot]);
}
}
}
using(var fileStream = new FileStream(path, FileMode.Create)) {
zipStream.Seek(0, SeekOrigin.Begin);
zipStream.CopyTo(fileStream);
}
}
}
I've used Microsoft's DocumentFormat.OpenXML and Excel Interop, however, they are both lacking in a few main components that I need.
Update:
using(var fileStream = new FileStream(path, FileMode.Create)) {
var wrapper = new StreamWriter(fileStream);
wrapper.AutoFlush = true;
zipStream.Seek(0, SeekOrigin.Begin);
zipStream.CopyTo(wrapper.BaseStream);
wrapper.Flush();
wrapper.Close();
}
Try the process without changing the string and see if the file size is the same. If so then it would seem that your copy is working correctly, however as Marc B suggested, with compression, even a small change can result in a larger change in the overall size.

C# Comparing two files and exporting matching lines based on delimiter

Here’s the scenario.
I have a text file(alpha), single column, with a bunch of items.
My 2nd file is a csv(delta) with 4 columns.
I have to have the alpha compare again the delta and create a new file (omega) in which anything that alpha matched delta, it would export only the first two columns from delta into a new .txt file.
Example:
(Alpha)
BeginID
(delta):
BeginID,Muchmore,Info,Exists
(Omega):
BeginID,Muchmore
This document will probably have 10k lines it in. Thanks for the help!
Here's a rough cut way of doing the task you need:
using System;
using System.Collections.Generic;
using System.IO;
using System.Text;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
string alphaFilePath = #"C:\Documents and Settings\Jason\My Documents\Visual Studio 2008\Projects\Compte Two Files\Compte Two Files\ExternalFiles\Alpha.txt";
List<string> alphaFileContent = new List<string>();
using (FileStream fs = new FileStream(alphaFilePath, FileMode.Open))
using(StreamReader rdr = new StreamReader(fs))
{
while(!rdr.EndOfStream)
{
alphaFileContent.Add(rdr.ReadLine());
}
}
string betaFilePath = #"C:\Beta.csv";
StringBuilder sb = new StringBuilder();
using (FileStream fs = new FileStream(betaFilePath, FileMode.Open))
using (StreamReader rdr = new StreamReader(fs))
{
while(! rdr.EndOfStream)
{
string[] betaFileLine = rdr.ReadLine().Split(Convert.ToChar(","));
if (alphaFileContent.Contains(betaFileLine[0]))
{
sb.AppendLine(String.Format("{0}, {1}", betaFileLine[0], betaFileLine[1]));
}
}
}
using (FileStream fs = new FileStream(#"C:\Omega.txt", FileMode.Create))
using (StreamWriter writer = new StreamWriter(fs))
{
writer.Write(sb.ToString());
}
Console.WriteLine(sb.ToString());
}
}
}
Basically it reads a txt file, puts the contents in a list. Then it reads a csv file (assuming no columns) and matches the values to create a StringBuilder. In your code, substitute the StringBuilder with creating a new txt file.
EDIT: If you wish to have the code run in a button click, then put it in the button click handler (or a new routine and call that):
public void ButtonClick (Object sender, EventArgs e)
{
string alphaFilePath = #"C:\Documents and Settings\Jason\My Documents\Visual Studio 2008\Projects\Compte Two Files\Compte Two Files\ExternalFiles\Alpha.txt";
List<string> alphaFileContent = new List<string>();
using (FileStream fs = new FileStream(alphaFilePath, FileMode.Open))
using(StreamReader rdr = new StreamReader(fs))
{
while(!rdr.EndOfStream)
{
alphaFileContent.Add(rdr.ReadLine());
}
}
string betaFilePath = #"C:\Beta.csv";
StringBuilder sb = new StringBuilder();
using (FileStream fs = new FileStream(betaFilePath, FileMode.Open))
using (StreamReader rdr = new StreamReader(fs))
{
while(! rdr.EndOfStream)
{
string[] betaFileLine = rdr.ReadLine().Split(Convert.ToChar(","));
if (alphaFileContent.Contains(betaFileLine[0]))
{
sb.AppendLine(String.Format("{0}, {1}", betaFileLine[0], betaFileLine[1]));
}
}
}
using (FileStream fs = new FileStream(#"C:\Omega.txt", FileMode.Create))
using (StreamWriter writer = new StreamWriter(fs))
{
writer.Write(sb.ToString());
}
}
I'd probably load alpha into a collection then open delta for read, while not EOF readline into a string, split, if collection.contains column 0 then write to omega.
Done...

Categories

Resources