Witam
Od jakiegoś czasu bawię się programowaniem sieciowym. Umiem już wysłać po TCP wiadomości i obsłużyć użytkowników.
Teraz mam tylko pytanie jak można wysyłać pliki. Wpadłem na pomysł wczytywanie pliku (nie ważne jakiego typu) strumieniem i wysyłanie go linijkami. Jest lepszy sposób na to?
Hę? jakimi linikjami? Program nie ma żadnych linijek. Przesyłanie pliku polega na wczytaniu np 1Kb do bufora, następnie przesłanie bufora przez TCP na drugą strone i tam doklejenie do poprzednich danych. I następna paczka.
Do tej pory wczytany plik wrzucałem do stringa, bo znam tylko ten sposób.
otwiersz plik
czytasz binarnie
przesylasz to co wczytales
odbierasz po drugiej stronie
zapisujesz binarnie
masz plik przeslany
Czyli zwykły StreamReader, a czytanie binarne na czym polega? Wujek pokazuje tylko jak czytać pliki binarne.
BinaryReader
Jak wiesz, program (tak jak wszystko na komputerze) składa się z ciągów zer i jedynek. 8 takich cyfr to bajt. Czytanie/Zapisywanie/Kopiowanie binarne polega na tym, że za pomocą odpowiedniej funkcji zamieniasz plik na np. tablicę byte[]
(która, jak sama nazwa wskazuje, potrafi pomieścić maks. 8 zer i jedynek), a następnie stworzenie nowego pliku i skopiowanie tam w tej samej kolejności tej samej tablicy byte[]
. W ten sposób otrzymujesz idealną kopię danego pliku (poza np. nazwą, którą wybierasz sam).
W twoim przypadku, program czytający wczytuje tablicę byte[]
i przesyła drugiemu programowi, który tworzy nowy plik i zapisuje w nim tablicę byte[]
. Jeśli chcesz, możesz to ulepszyć, np. wysyłając najpierw nazwę pliku, dzięki któremu otrzymasz nie tylko plik o identycznym działaniu, ale również tej samej nazwie.
http://pl.wikipedia.org/wiki/Bajt
http://pl.wikipedia.org/wiki/Oktet_%28informatyka%29
Jedno i drugie to 8 bitów, tak więc dużej różnicy nie ma
Zrobiłem to wysyłanie za pomocą BinaryReader ja polecił Utermiko.
Wrzuciłem plik wczytany za pomocą BinaryReadera (b) do StreamWritera (streamw) - streamw.Write(b)
Po czym wysłałem do drugiego klienta.
Następnie tworzę File stream do którego wpisuje za pomocą BinaryWriter.
Gdzieś popełniłem błąd, tylko nie wiem gdzie.
Wysyłanie:
StreamWriter streamw = new StreamWriter(nstream);
BinaryReader b = new BinaryReader(File.Open("c:\\serwer\\testyyy.png", FileMode.Open));
streamw.Write(b);
streamw.Flush();
b.Close();
Odbieranie:
StreamReader rstream = new StreamReader(nstream);
String dane = rstream.ReadLine();
FileStream writeStream;
writeStream = new FileStream("c:\\serwer\\cxz.png", FileMode.Create);
BinaryWriter writeBinay = new BinaryWriter(writeStream);
writeBinay.Write(dane);
writeBinay.Close();
Myślę że coś takiego bardziej by pasowało dla wysyłania i coś analogicznego dla odbierania bo ReadLine() to mi się jakoś nie widzi, Aczkolwiek z pewnością można ładniej.
BinaryWriter bw = new BinaryWriter(NetStream);
BinaryReader b = new BinaryReader(File.Open("c:\\serwer\\testyyy.png", FileMode.Open));
int BufPos = 0;
byte[] bufor = new byte[10];
while (b.PeekChar() != -1)
{
b.Read(bufor, BufPos, 1);
if (BufPos == 9)
{
bw.Write(bufor);
bufor = new byte[10];
BufPos = 0;
}
else
{
BufPos++;
}
}
bw.Close();
Poza tym nie wiem czy nie będzie brakowało znacznika końca pliku. Na pewno sw.write(b) nie będzie działać ponieważ wysyłasz obiekt jakim jest BinaryReader a nie to co przeczytał.
Pozdrawiam.