Laden...
S
Stefan S. myCSharp.de - Member
Capital City of Bavaria Dabei seit 20.05.2006 72 Beiträge
Benutzerbeschreibung

Forenbeiträge von Stefan S. Ingesamt 72 Beiträge

20.04.2012 - 22:19 Uhr

Es wundert mich das noch keiner geantwortet hat. Ich nutze die Library recht häufig. Respekt für die Arbeit an den Autor!

Die Software ist sehr sauber und logisch geschrieben. Ich habe lediglich bei den Matrizenoperationen ein paar performantere Algorithmen, z.B. den Strassen-Algorithmus, eingebaut.

Für einen E-Technik Absolventen jedenfalls ein schönes Stück Software. Da kann sich so manch ein Informatiker eine Scheibe von abschneiden.

20.04.2012 - 15:24 Uhr

Der Strang ist zwar schon alt, aber für das Protokoll. Ich fand den folgenden Artikel dazu recht gelungen.

Künstliche neuronale Netze in C#

Da ist auch eine umfassende Bibliothek dabei für KNNs, gecodet in C#. Auch die OCR kommt da zur Sprache. Eignet sich daher recht gut für Präsentationen.

15.08.2011 - 17:50 Uhr

Ein paar Aspekte, die Properties etwas kritischer beleuchten ohne sie für obsolet zur erklären.
*Ein Property kann schreibgeschützt sein oder darf nur beschrieben, aber nicht gelesen werden. Felder können immer gelesen und beschrieben werden. Das kann zu Verwirrungen im Code führen. *Ein Property kann eine Ausnahme auslösen, ein Feld nicht. *Ein Property kann nicht als out- oder ref-Argument übergeben werden. *Ein Property kann langsam beim Zugriff sein, die Entscheidung obliegt Designkriterien und dem Compiler, ob ein Inlining stattfindet. *Properties geben beim Zugriff mit einem Thread nacheinander eventuell unterschiedliche Werte zurück, ein Feld nicht. DateTime.Now ist ein Beispiel dafür. *Properties haben unter Umständen sichtbare Nebenwirkungen, der Feldzugriff nie. Der Benutzer eines Typs sollte in der Lage sein, verschiedene Eigenschaften, die in einem Typ definiert sind, in beliebiger Reihenfolge zu ändern, ohne dass sich das Verhalten des Typs durch die andere Reihenfolge ändert. *Ein Property benötigt unter Umständen zusätzlichen Ram oder gibt einen Verweis auf etwas zurück, das nicht Teil des Objektzustands ist. So kann eine Eigenschaft auch Kopien zurückgeben, was oft im Code nicht dokumentiert ist.

In Java gibt es aus gutem Grund keine Properties.

Ich persönlich sehe Properties als legitimes Werkzeug, aber man sollte sich vor Augen halten das Properties keine echten Vorteile bieten, bis auf die vereinfachte Syntax.

Und diese bringt durch die Uneindeutigkeit einige Probleme mit sich.

Ich werde in Zukunft wohl deutlich sparsamer mit ihnen umgehen und im Zweifelsfall "richtige" Methode implementieren. 😭

14.08.2011 - 21:49 Uhr

@gfoidl:
Ich habe keine Ahnung, wovon du hier sprichst, aber das hat mit meinen Worten mal wieder NULL zu tun! Und langsam nervt es mich ehrlich gesagt deine Belehrungen zu lesen, wenn du selbst derjenige bist, der hier Bahnhof versteht. 😭

Weder habe ich irgendetwas in Bezug auf Debugger geschrieben, noch ist deine Aussage über Jeffrey Richter korrekt. Der von mir verlinkte Blog hat mit Jeffrey Richter nichts zu tun. Jeffrey Richter ist ein langjähriger .NET-Experte und in seinem Buch "Microsoft .NET Framework - Expertenwissen zur CLR und .NET" geht dieser ausführlich auf Properties und ihre Nachteile ein. Und warum er diese ablehnt.

Der oben verlinkte Blog enthält eine wesentliche Zeile, die mir wichtig war und weshalb ich die Quelle verlinkt habe.

But there are no hard and fast rules and in most cases you shouldn’t have to worry about this, just let the compilers do their thing and certainly don’t try to out guess them. If you do want to see what your code looks like you’ll have to attach the debugger.

Das dort der Debugger aktiv war, das habe ich selbst gelesen. Das musst du mir hier nicht erklären.

In deinem Test-Beispiel kannst du RCE erreichen indem folgendes geschrieben wird:

  
double[] array = testTime2.Array;  
for (int i = 0; i < array.Length; ++i)  
{  
    //  
}  
  

Dadurch wird die Array-Referenz in den lokalen Stack der Methode geholt und der JITer kann die RCE durchführen. Aber das hättest du auch über die (Foren-) Suche, auf die du hingewiesen wurdest, finden können.

Das ist schön, mir aber auch schon bekannt und es ändert auch nichts an den gemessenen Zeiten. Time2 bleibt weiterhin langsamer als Time1, natürlich mit Optimierung im Release Mode!

Erst wenn sämtliche direkten Property-Aufrufe entfernt werden, bekomme ich identische Laufzeiten und dann kann ich auch gleich direkt Arrays verwenden, weil dann brauche ich keine Properties.

for (int i = 0; i < array.Length; i++) {
    array[i] = i;
    i = (int)array[i];
}

Bitte etwas mehr Eigeninitiave und genau lesen was wo steht, sonst drehen wir uns hier im Kreis und das bringt niemanden etwas.

Der ist gut! Mir mangelnde Eigeninitiative vorwerfen, das hatte ich schon lange nicht mehr. Die treffenden Links und Quellcodes haben sich wohl selbst gefunden und geschrieben?

Hast du auch ohne Debugger gemessen?
Im Release Build?
Außerdem ist es keine gute Idee, nur eine Messung durchzuführen - führe lieber in einer Schleife ein paar tausend aus nimm dann die besten.

Natürlich im Release-Build. Es werden in der Schleife rund 10000000 Iterationen durchgeführt. Das reicht allemal.

Zumal mir meine Vermutung eindrucksvoll bestätigt wird. Wenn etwas geht wie eine Ente, Quakt wie eine Ente, dann ist P hoch, das es eine Ente ist.

14.08.2011 - 17:54 Uhr

Hier auch ein kleiner Blogartikel zu Properties.

C# Inline Methods and Optimization

Jetzt weiß ich auch warum Jeffrey Richter Properties nicht mag und in seinem Buch von ihnen abrät.

Man geht sehr schnell viel zu leichtfertig mit ihnen um.

14.08.2011 - 02:17 Uhr

Im Profiler wurde mir nun relativ schnell klar das die verwendete Matrixklasse unzufriedenstellende Resultate liefert.

Eigentlich wollte ich das schon vorher im Profiler testen, habe es aber bisher aufgeschoben.

Hatte mich damals entschieden die Math.NET Library für diverse Matrizenrechnungen zu verwenden. Man muss das Rad ja nicht vollständig neu erfinden.

Nun zeigte sich aber das die Multiplikation, sowie die Skalarmultiplikation von Vektoren enorm viel Zeit beansprucht. Obwohl ich den meisten Overhead aus der Library entfernt habe, ist die Klasse dort immer noch ineffizient.

Ich habe nun die Math.NET interne Multiplikation durch den Strassen-Algorithmus ersetzt, der bei meinen großen Matrizen deutliche Vorteile bringt.

Funzt wunderbar und hat die Performance gleich mal um rund 20 % erhöht. 👍

Den Performanceinbruch führe ich hauptsächlich auf die Properties zurück. Obwohl ich die List durch ein Array ersetzt habe und direkt die Länge abfrage, ist die Performance schlecht geblieben.

Liegt also tatsächlich nur teilweise am Range Check, sondern vielmehr an den Property-Zugriffen. Mit inlinen scheint da nicht viel zu laufen.

Hier ein kleines Testprogramm:

namespace PropertiesPerformanceTest
{
    class TestTime1
    {
        public TestTime1() 
        { 
        }

        public double[] arr = new double[10000000];
    }

    class TestTime2
    {
        public TestTime2() 
        { 
        }

        public double[] Array 
        {
            get { return arr; }
        }

        public int getLength
        {
            get { return arr.Length; }
        }

        private double[] arr = new double[10000000];
    }

    class Program
    {
        static void Main(string[] args)
        {
            try {
                TestTime1 time1 = new TestTime1();
                TestTime2 time2 = new TestTime2();
                Stopwatch watch1 = new Stopwatch();
                Stopwatch watch2 = new Stopwatch();
                watch1.Start();
                for (int i = 0; i < time1.arr.Length; i++) {
                    time1.arr[i] = i;
                    i = (int)time1.arr[i];
                }
                watch1.Stop();
                watch2.Start();
                for (int i = 0; i < time2.getLength; i++) {  // little bit faster with time1.arr.Length
                    time2.Array[i] = i;
                    i = (int)time2.Array[i];
                }
                watch2.Stop();
                Console.WriteLine("Time for 1={0} and 2={1}", watch1.ElapsedMilliseconds, watch2.ElapsedMilliseconds);

            } catch (Exception ex) {
                Console.WriteLine(ex.Message);
            }
            Console.In.ReadLine();
        }
    }
}
13.08.2011 - 22:53 Uhr

Bin schon dabei mit SlimTune Mir die Profilergebnisse im Detail anzusehen. Werde berichten.

13.08.2011 - 22:45 Uhr

Wie soll ich sonst die Arraylänge testen, wenn Count ein Property von IList ist?

13.08.2011 - 22:31 Uhr

Ja, das tausche ich bereits aus, nämlich mit:

int count = myObject.Count;

for (int j = 0; j < count; j++) {
   // ...

Ich werde berichten, ob das Besserung gebracht hat.

Wollte nur wissen, ob das auch beim Indexer passiert...

Danke!

13.08.2011 - 22:27 Uhr

Hallo gfoidl!

Ok, habe mir mal ein wenig die Microsoft Seite angesehen.
Writing High-Performance Managed Applications : A Primer

Da steht auch der Punkt über die Range Check Elimination.

Ich bin mir nur nicht sich sicher wo genau er das durchführen könnte? Beim myObject.Count?

Oder wenn auf das Objekt über den Index zugegriffen wird?

public MyObject this[int index]
{
    get { return _myList[index]; }
}

Gruß,
Stefan

13.08.2011 - 22:07 Uhr

Hallo,

Ich bastle gerade an einem Programm über neuronale Netze, Stichwort Backpropagation.

Das Programm funktioniert einwandfrei, nun aber wollte ich das Klassendesign ein wenig überarbeiten.

Ich hatte bisher direkte Arrays, genauer gesagt zwei vom Typ Jagged Array (double[][]).

Ich wollte nun diese in Klassenobjekten kapseln, um Trainingsmuster dynamisch anzulegen.

Leider musste ich nun feststellen das die wenigen Zugriffszeilen, die ich im Algorithmus ausgetauscht habe, die Performance haben komplett einbrechen lassen.

Zuvor stand z.B.

myArray[i][j]

drin, nun steht

myObject[i].Input[j]

drinnen, wobei Input ein Property ist, das double[] zurück gibt. Oder

myArray.Length

ersetzt durch

myObject.Count

Count ist auch ein Property und liefert direkt List.Count zurück.

Der Indexer this[int index] liefert auch direkt List[index] zurück.

Die paar Zeilen, die ausgetauscht worden sind verändern das Laufzeitverhalten dramatisch.

Was macht die CLR hier? Warum bricht die Performance so weg? 🤔

Ich weiß zwar das Properties unter Umständen ziemlichen Overhead verursachen, vor allem wenn der Compiler nicht inlinen kann, aber das ist schon extrem.

06.12.2010 - 17:07 Uhr

Moin zusammen,

Ich entwickel im Moment mit einem Kumpel zusammen an einem rundenbasiertem Strategiespiel.

Das Spiel soll auch einen kleinen lokalen Netzwerkmodus haben. Wir haben uns für ein Client-Host System entschieden. Doch hapert es im Moment an der Umsetzung.

Schau dir doch einmal das folgende Beispiel:

http://www.codeplanet.eu/tutorials/csharp/66-client-server-modell.html

Da steht alles was du wissen musst mit Code.

04.09.2010 - 18:25 Uhr

Wie kann ich, wenn ich eine Verbindung besteht und ich auch Daten senden kann, unterscheiden welche Art von den Daten kommen.

Momentan bekomm ich ja nur die Strings der Chat Nachricht, wenn ich jetzt aber einen anderen String senden möchte, der keine Nachricht ist sondern einen anderen Zweck erfüllen soll. Wie kann ich das Programm dann am besten unterscheiden lassen was die Daten für die Nachricht sind und welche die anderen Daten sind.

Meine erste Idee war ein Sonderzeichen einfügen z.b. jede chatnachricht bekommt eine # voran gestellt und das dann durch ein if abfrage filtern, aber so könnte es zum Problem kommen wenn jemand die Sonderzeichen im Chat verwendet.

Ich denke da müsste es doch eine bessere Lösung für geben als jeden Datensatz im Server zu verändern und im Client zu korrigieren.

Eigentlich wird das in dem oben von mir genannten Link auch besprochen. Du kannst ein eigenes Nachrichtenpaket entwerfen, wo eben der Nachrichtetyp vorhanden ist und über TCP mitgeschickt wird. Das kann ein Int32 sein, definiert über ein Enum.

Schau dir das Tutorial und den Source dort mal genauer an. Da wird alles genau beschrieben.

Client-Server-Modell

EDIT: Kann hier leider keine Bilder verlinken. 🙁

04.09.2010 - 18:16 Uhr

Hallo zusammen,

habe mich schon dumm und dämlich gesucht, jedoch nichts gefunden was mir weiterhelfen könnte. Falls ich etwas übersehen habe tut es mir wirklich leid.

Ich muss einen TCP Client schreiben, welcher ein Telegramm mit einer bestimmten Datenstruktur an einen Server sendet.

Die Datenstruktur ist unterteilt in einen Header und ein Datenpaket und sieht ungefähr so aus:

Header:
Nachrichtenlänge (short): Länge des Telegramms inkl. Header in Bytes...also z.B. 74
Nachrichten-ID (short): z.B. 200
Aufsteigender Zähler (ushort): Ein Zähler der bei jedem Senden um 1 erhöht wird.

Datenpaket: (Diese Struktur wird auf Client und Serverseite festgelegt, die Reihenfolge und Anzahl der Werte kann also beliebig sein)

Ein Wert Int16,
Ein Wert Int32
etc.

Guckst du hier.

Client-Server-Modell

Dort kannst du sehen, wie Nachrichtenpakete serialisiert und über TCP übertragen werden.

Dort wird ein ganzes Datenpaket mit Header übertragen und empfangen!

Auf Little und Big Endian wurde ja bereits hingewiesen.

27.08.2010 - 22:56 Uhr
        // Die Methode sendet eine HTTP GET 1.1 Anfrage an den Server und
        // empfängt die Daten
        private static string SocketSendReceive(string server, int port)
        {
            Socket sock = null;

            // Die zu sendenden Daten
            string request = "GET / HTTP/1.1\r\nHost: " + server +
                             "\r\nConnection: Close\r\n\r\n";
            // Kodiere den string in Bytes
            byte[] bytesSent = Encoding.ASCII.GetBytes(request);
            // Lege ein Byte Array an für die zu emfangenden Daten
            byte[] bytesReceived = new byte[4096];

            // Instanziere ein gültiges Socket Objekt mit den übergebenen Argumenten
            sock = ConnectSocket(server, port);

            if (sock == null)
                return ("Connection failed!");

            // Sende den HTTP-Request
            sock.Send(bytesSent, bytesSent.Length, SocketFlags.None);

            int bytes = 0;
            string page = "Default HTML page on " + server + ":\r\n";

            // Empfange die Daten und konvertiere sie
            do {
                bytes = sock.Receive(bytesReceived, bytesReceived.Length, SocketFlags.None);
                // kovertiere die Byte Daten in einen string
                page = page + Encoding.ASCII.GetString(bytesReceived, 0, bytes);
            } while (bytes > 0);

            // Unterbinde alle weiteren Send() und Receive() Aktivitäten am Socket
            sock.Shutdown(SocketShutdown.Both);
            sock.Close();

            return page;
        }

Siehe TCP/IP Socket-Programmierung in C#

27.08.2010 - 22:52 Uhr

Ich habe nämlich noch keine Möglichkeit gefunden, wie mein Programm das mitbekommt, das die Hostanwendung geschlossen wurde... Da ist noch der Haken...

Bin für weitere Tipps dankbar.

Regelmäßig einen Zero-byte Nonblocking Call durchführen.

socket.Send(new byte[1], 0, 0);

Anschließend Exception auffangen.

Siehe TCP/IP Socket-Programmierung in C#

24.08.2010 - 22:22 Uhr

Schau dir mal die asynchronen Methoden an, mit denen kannst du auf eine Nachricht warten und kriegst dann sozusagen ein Event aufgerufen wenn eine kommt. Dazu gibts sicher auch einige Beispiele.

Richtig, guckst du hier. 😉

Client-Server-Modell

Dort wird entsprechend mit Events gearbeitet. Es steht auch ein genzes Protokoll zur Verfügung, auch bestens geeignet für einen Chat Server/Client!

06.05.2010 - 00:20 Uhr

Hallo,

ich spiele grade mit dem Datenaustausch zwischen threads rum, angenommen ich habe X Threads und ich erstelle ein Semaphore,

wenn ich meinen kritischen Code innerhalb von

   
sema.Semaphore.WaitOne();  
// code  
sema.Semaphore.Release();  

bin ich auf der sicheren seite?
kann ich unterschieden zwischen "lesen" und "schreiben", es können ja mehrere threads auf die selbe variabel lesend zugreifen.

Nein, eine Unterscheidung zwischen Threads ist nicht möglich. Semaphore spezifiert nur wieviele Threads den Codeabschnitt betreten dürfen, nicht welche das sind.

Das wäre auch unsinnig, du programmierst den Code der Threads schließlich selbst.

Alles weitere, siehe:

Die Klasse Semaphore und Synchronisationsblöcke

30.04.2010 - 17:50 Uhr

Hallo zusammen

Gibt es eine Möglichkeit, sich auf Basis des TCP-Protokolls mit mehreren Clients gleichzeitig zu verbinden? Es handelt sich dabei um ein Peer-To-Peer Netzwerk.
Zwar liese sich das Problem mit UDP lösen, da es bei diesem Protokoll gar nicht erst eine Verbindung benötigt allerdings ist UDP nicht sonderlich sicher.

Selbstverständlich ist das möglich. TCP ist eine reine Unicast Verbindung. Das bedeutet aber nicht, das du nicht mehrere Verbindungen herstellen kannst.

Große P2P Programme, wie eMule nutzen auch TCP. Threading und asynchrone I/O machen es möglich.

Ein Tutorial gibt es hier.

http://www.codeplanet.eu/tutorials/csharp/4-tcp-ip-socket-programmierung-in-csharp.html

Ganz nett ist auch das hier.

http://www.codeplanet.eu/tutorials/java/57-battleship.html

Dort wird eine P2P-Bibliothek mit TCP vorgestellt.

25.02.2010 - 22:26 Uhr

Naja @Stefan - Ich bin eigentlich froh, dass z.B. ein Arzt nicht wissen muss wie ein CT funktioniert um damit eine Diagnose stellen zu können, da reicht es wenn da ein Physiker weiß, was im Hintergrund passiert.

Natürlich sollte man als Entwickler wissen, womit man arbeitet - aber für ein paar Hobby-Hacker reicht es wohl zu wissen, dass man mit dem TcpClient rummurksen kann.

Naja, der Vergleich kommt aber mit einem Hinkebein angehumpelt. Ein Programmierer, der einen TcpListener nutzt, sollte schon wissen wie TCP funktioniert, sonst wird er nämlich beim Versenden von Daten sehr bald große Augen bekommen.

Korrekter wäre der Vergleich, Endanwender (Arzt) nutzt die Chatsoftware, Entwickler (Ingenieur, Physiker) baut die Software.

Ich glaube, heutzutage wird oft die Situation von Anfängern verkannt.
Für euch Profis gehört das meiste schon zum Selbstverständlichen und ihr könnt nur den Kopf schütteln, wenn eine total dumme Frage kommt.

Ich für meinen Teil bemerke zum Beispiel das Lehrsystem in Schulen - unsere gymnasialen Informatiklehrer sagen zu einem, wenn man den Bildschirmhintergrund ändert, "Du hackst hier die PCs, ich sag dem Direktor bescheid!". Das ist weder ein Witz noch eine Übertreibung, das hats bei uns gegeben.
Aus schulischer Perspektive lernt man leider anscheinend auch viele "Fachbegriffe" falsch. Mit optimiertem Code meinte ich vermutlich nicht dass, was ihr meint. In schulischer Ausbildung sind Exception-Handler nämlich schon optimierter Code. Exceptions sind einfach die Punkte, wo der Informatiklehrer sagt "Keine Ahnung warum dein Programm nicht läuft.". Und weggeht.

Solche "Informatiklehrer" soll es geben, das stimmt. Es gibt sogar viele Lehrer, die einfach falsche Grundlagen vermitteln und auf diese Weise dazu beitragen das die Schüler die Konzepte nicht richtig begreifen.

Jetzt ist natürlich klar: Wer nur über die Schule versucht, Programmieren zu lernen, ist völlig verloren. Das durchwühlen des Internets gehört dazu - meiner Meinung nach aber auch das Nachfragen in Foren bei Unverständniss. Das Problem hierbei: Wenn man in einem Turorial etwas nicht versteht, und deshalb nachfragt, wird man auf das Tutorial zurückverwiesen.
Zum Lernen suche ich meist erstmal die leichteste Methode, um das Problem zu lösen.
Die paar Zeilen, nach denen ich gesucht hatte, wären z.B. gewesen:

Kann ich nachvollziehen. Aber mal ehrlich, diese Zeilen findest du auch in dem von Joetempes verlinkten Tutorial. Der Unterschied ist, du benutzt hier eine überliegende Klasse, statt direkt Sockets zu nutzen.

Bis ich die paar Zeilen aus den ganzen Tutorials und Forenbeiträgen rausgefischt habe, sind inzwischen bestimmt 2-3 Wochen vergangen - Zeit, die man, gerade beim Programmieren für die Schule, überhaupt nicht hat.

Dann müsstest du sagen, du benötigst schnelle Hilfe und kannst dich nicht mit den Grundlagen befassen, weil du Ziel XY erreichen willst.

Dir ist natürlich bewußt, dass du ein generelles Problem hast, wenn du dich nicht richtig mit den Details befasst. Du verfügst dann über gefährliches Halbwissen. Zum Beispiel kann ich dir die Frage stellen, was Flush() bewirkt und warum es bei einem StreamWriter funktioniert, bei einem NetworkStream aber nicht.

Die paar Zeilen, nach denen ich gesucht hatte, wären z.B. gewesen:

So tragisch ist der Code auch wieder nicht. Ein wenig Exception Handling ist dabei, ansonsten dasselbe in weiß.

Ihr könnt euch das wahrscheinlich garnicht mehr vorstellen, aber einem C#-Anfänger fallen da erstmal die Augen raus. Dann versucht er, irgendwie rauszufiltern welche Befehle jetzt eigentlich für das Senden und Empfangen an sich zuständig sind, immer wissend, dass man auf sich alleine gestellt ist, denn wenn man fragt wird man auf genau dieses Tutorial verwiesen. Häufig wird zwar nett angeboten, dass man für einzelne, unverständliche Zeilen nachfragen kann und das wird einem dann auch nett erklärt, aber als Anfänger sieht man sich leider meistens in der Lage, dass man die Augen schließen könnte und mit dem Finger auf irgendeine Zeile zeigt, und egal welche es ist, man versteht sie garantiert nicht. Der ganze Kram, der um die eigentlichen paar Zeilen steht, ist zwar meistens durchaus sinnvoll, aber er verwirrt. Ich für meinen Teil werde auch früh genug verstehen, dass es ständig zu Exceptions kommt und da mal ein paar Handler reinmüssen - das ist der Punkt, wo ich danach suche und lerne, das Tutorial jetzt vielleicht verstehe. Sowas kommt von alleine.

Klar ist das kein Zuckerschlecken, aber du kannst auch nicht erwarten mit Integraltransformationen zu rechnen, bevor du nicht das Integrieren gelernt hast.

Wie ich bereits sagte, du kannst dir natürlich prinzipiell ein funktionierendes Programm zusammenstellen, doch das ist dann mehr Try-and-Error, eine Art Bastelstunde mit Code. Wenn du wirklich solide Programme schreiben möchtest musst du ganz unten beginnen und das braucht nunmal Zeit. Da mussten auch heutige Profis einmal durch.

Zum Thema Grundlagenforschung:
Ich glaube, wenn man das so betreibt wie ihr empfehlt, kommen da so Leute wie Informatiklehrer raus. Wenn ich alles von Grund auf erschließen wollte, würde ich mit ASM anfangen, dann langsam zu C wechseln, vielleicht Cobald, Ruby und so einen Kram lernen, dann irgendwann mal Pascal, C++... Leider wäre ich dann aber schon so alt und es gäbe schon so viel Neues, dass ich nur noch Informatiklehrer werden könnte.

Glaube mir, Informatiklehrer kommen da bestimmt nicht heraus. 😁

Wenn du Informatik studierst musst du auch die Grundlagen erlernen. So ist das nunmal.

Es ist nicht notwendig ASM zu kennen, um mit C# zu entwickeln. Aber du solltest mit der Syntax und den Sprachfeatures von C# vertraut sein und dazu gehören Exceptions. Es ist auch wichtig die Prinzipien der objektorientierten Programmierung zu begreifen, als auch den Vorgang, was bei der Kompilierung von C#-Code herauskommt.

Bei der Netzwerkprogrammierung ist ein rudimentäres Wissen über das IP, TCP und UDP einfach unerlässlich. Du kannst auch nicht am Ottomotor rumschrauben, wenn du nicht weißt, wie eine Zündkerze aussieht und wozu sie da ist.

Ich glaube auch nicht, dass es unbedingt an meiner Intelligenz/Qualifikation liegt. Ich besuche das beste Gymnasium meiner Stadt, mache nächsten Monat das Abitur mit 17 Jahren, stand in Informatik immer auf der maximalen Punktzahl und mir wird dringend empfohlen, im Oktober mein Informatikstudium in Aachen aufzunehmen.

Mit 17 bist du noch jung, also keine Panik. Solltest du Informatik studieren, wirst du nach deinem Abschluss wissen was ich gemeint habe, als ich sagte das ohne die Grundlagen einfach kein guter Informatiker die Uni verlässt.

Es gibt mittlerweile einen ganzen Haufen selbsternannter Programmierer und Experten im Netz und im Reallife, die alleine nichts vernünftiges erarbeiten können, weil sie einfach keine echte Ahnung haben. Mir sind schon etliche begegnet. Ich kam auch ganz selten in den Genuß mit absoluten Spitzenleuten zusammenarbeiten zu dürfen, von denen man sehr viel lernen konnte.

Aber diese Experten sind rar und in der Industrie heiß begehrt.

25.02.2010 - 01:27 Uhr

Oder muss ich etwa eine TCP-Client zu TCP-Client Verbindung machen, nur wie geht das dann?

Grundlagen lernen, dann klappts auch mit dem Verständnis. Es gibt keine "TCP-Client zu TCP-Client Verbindung".

http://www.codeplanet.eu/tutorials/csharp/4-tcp-ip-socket-programmierung-in-csharp.html

Im MSDN Magazin gab es vor einigen Jahren ebenfalls einen recht umfangreichen Anfängerartikel, einfach mal Google verwenden.

25.02.2010 - 01:08 Uhr

Hey, danke, das ist für mich schonmal hilfreicher als die ganzen Tutorials, in denen ich nur optimierten fertigen Code finden konnte.

Was für optimierten Code? In dem von Joetempes verlinkten Tutorial wird bei Adam und Eva begonnen. Da gibts keinen optimierten Code. In keinem Anfänger Tutorial wird optimierter Code verwendet. In der Netzwerkprogrammierung für Anfänger auch völliger Nonsens, weil Codeoptimierung Aufgabe der CLR ist und hauptsächlich Algorithmen betrifft und die gibt es in den besagten Tutorials nicht.

Und was erwartest du eigentlich? Exception-Handler sind ein fundamentaler Bestandteil bei der Programmierung. Du wirst wohl noch den Exceptioncode vom Netzwerkcode trennen können.

Ich verstehe die Leute nicht, die sich mit der Netzwerkprogrammierung befassen wollen und dann schon an trivialen Artikeln scheitern. Dann wird am TcpListener rumgedoktert, während man nicht einmal weiß was ein Socket ist oder was überhaupt die Vor- und Nachteile von TCP sind.

Warum schreibt ihr nicht gleich etwas in der Art.

SimpleChat chat = new SimpleChat();

Dann spart ihr euch die ganze Programmierarbeit mit einem Einzeiler und könnt mit dem Chatten loslegen. Oder nehmt gleich ICQ, ist noch einfacher.

07.02.2010 - 17:41 Uhr
  1. Wenn ich nun mit einem Server und 11 Clienten arbeite, kann es ja pasierern, dass der Server gerade Datenpakete rausschickt und gleichzeitig der Client etwas zum Server schickt, aber der ist ja beschäftigt.
    Um dort aufkommende Problem zu vermeiden, sollte ich dann das Ganze ins Threads verwalten oder ist das unnötig?

Das stellt kein Problem dar, weil empfangene Daten im TCP-Buffer landen. Allerdings macht es Sinn pro Clienten einen Workerthread zu verwenden.

  1. Wenn ein Client etwas zum Server schikt, was dann an alle anderen Clienten geschikt werden soll mit der Info von welchem Clienten es kam, brauche ich doch die IP des Clienten von dem es ursprünglich kam, oder?
    Wie ich die IP nicht ermitteln? Weil dazu finde ich nix passendes.

Die IP ist direkt an den Socket gebunden und wird mit der Eigenschaft RemoteEndPoint aufgerufen.

06.02.2010 - 20:30 Uhr
  1. Aber kann man denn nun noch überhaupt sicherstellen irgendwie, das das Paket auch bei allen angekommen ist, da das UPD nicht überprüft (wie TCP)

Mit UDP gibt es keine Garantie dafür dass das Paket auch ankommt, das ist richtig.

  1. Für die Limitierung, dass nur 11 Clienten es maximal empfnagen dürfen und zwar nur die, die am selben "Pokertisch" sitzen. Dafür bräuchte ich wieder Multicast, oder.

Ja, wenn nur eine bestimmte Gruppe in dem Netzwerk die Daten empfangen soll, dann geht das nur mit Multicast. Du kannst das auch mit TCP lösen, dann musst du eben an jeden die Daten einzeln schicken.

Ich les auch an vielen Stellen, aber ich habe das Gefühl das auf vielen Seiten auch was falsches steht oder schlecht erklärt.

Auf der von mir oben verlinkten Seite steht nichts falsches und es ist dort eigentlich auch verständlich erklärt.

Ich würde nicht hier fragen, wenn ich jemand anderen wüsste, der es mir bestätigen könnte oder nciht, was ich mir zusammenlese und daraus entnehme, aber ich stehe leider etwas unter Zeitdruck und kann nicht erst auf zu vielen irrwegen wandeln, denn eigentlich sollte dieser Part der Arbeit wer anderes machen, aber der hat schlichtweg keinen Bock.
Von daher danke ich für die nachsicht.

Zeitdruck ist beim Erlernen von Netzwerkgrundlagen keine ideale Voraussetzung. Das Thema ist nämlich durchaus komplex, es reicht nicht aus mit C# programmieren zu können, man muss auch wissen was man macht und wie das alles eigentlich funktioniert.

Ich empfehle hierzu auch das folgende Heft.

http://www.tecchannel.de/sicherheit/news/421455/neues_tecchannel_compact_netzwerk_know_how/

06.02.2010 - 20:01 Uhr

Torrent und eMule sind P2P-Anwendungen. Was das ist kannst du auf Wikipedia nachlesen.

Beim Broadcast muss niemand "drinnen" sein. Das Internet Protokoll 4 und 6 definieren Broadcast-Adressen, wie z.B. 255.255.255.255. Sobald du in einem Netzwerk ein UDP-Paket an diese Adresse schickst, leitet das Netzwerk automatisch das Paket an alle Teilnehmer in diesem Netzwerk weiter.

Das funktioniert natürlich nicht im Internet, weil Internet-Router Broadcasts nicht weiterleiten, sondern nur in lokalen Netzen. Würde ein Broadcast auch im Internet funkionieren wäre das Netz schnell tot, weil es mit Paketen überflutet würde.

06.02.2010 - 12:01 Uhr

Mal ne kurze Frage zwischendurch, ob ich das richtig verstanden habe.

Da ich ja nur maximal 11 Clienten und 1 Server im Netzwerk habe könnte ich das Ganze über Broadcast versenden. Aber über Multicast scheint es einfacher zu realisieren zu sein in C#.

Ein Broadcast ist genauso einfach wie ein Multicast. Er ist sogar noch einfacher.

Frage 1: Wenn ich Broadcast/Multicast nutze, geht das nur über UDP oder auch über TCP?

Nein, das geht nur über UDP. Es kann zwangsläufig nicht mit TCP gehen, weil TCP immer Unicast ist. Du stellst schließlich eine Punkt-zu-Punkt Verbindung in TCP her.

Frage 2: Muss ich die Verbindung die zwischen Client und Server besteht nach jeden übertragen von Daten wieder schließen und neu öffnen wenn es wieder was zu übertragen gibt, oder kann die Verbindung bestehen bleiben auch wenn beide mal 2,3 Minuten nicht kommunizieren. Oder kommt dann nach einer bestimmten Zeit sowas wie ne Zwangstrennung, weil keiner was sagt.

Bei UDP besteht keine Verbindung zwischen Client und Server, weil UDP ein verbindungsloses Transportprotokoll ist.

05.02.2010 - 10:59 Uhr

Für Deinen Anwendungsfall reicht ein ganz simpler TCPListener und ein TCPClient

Was nutzt ihm ein TCPListener, wenn er nichtmal den Unterschied zwischen einer IPv4 und einer IPv6-Adresse kennt?

05.02.2010 - 09:56 Uhr

Wo hast du diesen Clienten her? Der gehört nicht zum Server!

Die Fehlermeldung ist eigentlich eindeutig. Der Server verwendet IPv6, dein Client nutzt aber eine IPv4 Adresse.

Deshalb heißt es in der Fehlermeldung auch.

Es wurde eine Adresse verwendet, die mit dem angeforderten Protokoll nicht kompatibel ist

05.02.2010 - 01:52 Uhr

Ich such nochmal in der socketklasse nach Timeouts, im moment stellt das Programm erst nach mehreren Sekunden den Disconnect fest. Das müsste doch irgendwie schneller gehen.

Wer beendet die Verbindung eigentlich? Normalerweise läuft unter TCP der Verbindungsabbau (FIN) geordnet ab, so dass beide Seiten informiert werden. Dazu sendet der abbrechende Peer ein Nullbyte.

In deinem Beispielcode passt zudem folgende Zeile nicht.

tcpClient.Client.Send(tmp, 0, SocketFlags.None);

Das muss

tcpClient.Client.Send(tmp, 1, SocketFlags.None);

lauten.

05.02.2010 - 00:13 Uhr

das ist es ja eine Fehlermeldung kommt nicht. Einfach nur keine Rückmeldung vom Programm mehr und das wars.

Was heißt keine Rückmeldung? Was macht das Programm dann? Und von welchem Programm ist hier eigentlich die Rede?

z.B. Kapiere ich nicht wozu ich eine Echo-Server brauche. ich will die Daten ja nicht wiederbekommen, die ich an den Server geschickt habe die sollen an alle anderen Clienten geschickt werden.

Wer hat gesagt das du einen Echo-Server brauchst? Dort ist mitunter ein Echo-Server beschrieben, der Daten wieder zurücksendet. Dort ist noch vieles andere beschrieben.

Fast der kompletten ersten beiden Seiten der Code dort, wenn der ausgeführt wird, geht eine konsolenfenster auf und sofort wieder zu, bevor ich etwas sehen kann.

Puh, dein Wissen hält sich doch sehr in Grenzen. Ein Konsolenfenster schließt sich automatisch, sobald das Programm beendet hat. Öffne zuerst eine Kommandozeile (cmd.exe) und rufe dann aus der Kommandozeile das Programm auf.

Der kram mit HTTP ist nicht nötig soweit ich weiß, da ich ja nur im Netzwerk agiere und keinen Internetanschluss brauche und auch niemals darauf zugreifen will.

Niemand hat gesagt das du HTTP verwenden sollst, wenn du es nicht brauchst.

Eine IP-Adresse muss ich auch nicht auflösen aus einer Domaine, da ich diese kenne, genauso wie den Port und alle anderen wichtigen Adressen, da wir die einfach festgelegt hat und somit nicht erst wegen der Dynamic ermitttelt werden müssen.

Du zählst andauernd Dinge auf, die du nicht benötigst. Warum konzentrierst du dich nicht auf das was du benötigst? Dort wird mit der Klasse Socket, TcpClient, UdpClient uvm. alles detailliert erklärt, was du wissen musst. Mit dem Wissen solltest du problemlos das programmieren können, was du willst.

Für deinen Fall solltest du dir sehr genau das Thema Multicast durchlesen!

Und ab Seite 3 schlackern mir dann die Ohren und ich klomme nicht mehr hinterher. Aber auch das Durchlesen der 2 Seiten davor macht mich nicht schlauer für seite 3

Ich kann mir auch nicht vorstellen ,das alle 7 Seiten wichtig sind, einfach nur einen String von PC a nach PC b zu schicken und das der Server irgendwann, wenn man es ihm sagt einen Sieger ermittelt ( geht um ien Pokerspiel über Netzwerk)

Natürlich sind nicht alle 7 Seiten für dein Vorhaben wichtig. Lies dir halt das durch, was du brauchst. Du solltest lernen wie man mit Sockets arbeitet, wie man einen UdpClient verwendet und was ein Multicast und Broadcast ist. Schließlich willst du Daten an eine Gruppe (b, c, d) senden.

Allerdings musst du dir die Grundlagen schon selbst durchlesen. Von alleine kommt das Wissen nicht in dein Hirn geflogen.

04.02.2010 - 21:10 Uhr

ja genau den Link hatte ich schon und habe mir das 2 Tage lang unter anderem durchgelesen aber ich bin nur verwirrt.

Was soll das heißen du bist "verwirrt"? Da ist alles relativ simpel in klarem deutsch erklärt, sogar mit vollständigen Beispielcode.

Vorallem wenn ich einem 2. client auf dem selben Rechenr starte, fängt alles an zu spinnen und schmirt ab und ich schnall nicht, ob das so gewollt ist oder nicht. Denn ich habe ja mehr als nur 1 Client.

Gar nix fängt an zu "spinnen". Und was heißt das eigentlich? "Spinnen" ist keine Fehlermeldung!

Man hat lokal (127.0.0.1) einen Server z.B. auf Port 355 und startet dann einen Clienten der zu diesem Port verbindet.

04.02.2010 - 20:16 Uhr

Nachdem ich viel gelesen habe, bin ich aber irgendwie noch genausoschlau wie am Anfang.
Das Ganze mit Win Sockets hat mich nur verwirrt .

Dann wird es Zeit für das hier.

http://www.codeplanet.eu/tutorials/csharp/4-tcp-ip-socket-programmierung-in-csharp.html

04.02.2010 - 14:56 Uhr

Ob du verbunden bist, kannst du mit einem nicht blockierenden, Zero-byte Send() prüfen und anschließend den Rückgabewert auswerten. Das hast du ja bereits in deinem Beispielcode gemacht. Dass das ganze Zeit in Anspruch nimmt, ist klar. Stell dir vor die Gegenstelle hat einen Stromausfall. Ein Verbindungsabbau mit FIN kommt so nie zustande. Du musst also explizit die Verbindung prüfen.

Bei einem TcpClient hast du kein Zugriff auf TCP-Flags (ACK, SYN, etc.), das ist gerade der Sinn von Protokollen. TcpClient hat auch keine Timeout Eigenschaft für synchrone Aufrufe. Da musst du schon direkt mit der Klasse Socket arbeiten und dort ist der Standardwert 0.

31.01.2010 - 13:16 Uhr

Dummerweise gibt es für Websockets bereits etliche Implementierungen im Java-Bereich - ob Draft oder nicht. Für Entscheider wieder mal ein Beweis: Im Zweifelsfall auf Java setzen...

Die offizielle Java-API unterstützt das Web Socket Protokoll auch nicht offiziell. Es gibt in Java freie und unabhängige Implementierungen für das Web Socket Protokoll.

Du kannst ja gerne eine für .NET schreiben.

31.01.2010 - 00:20 Uhr

Für Websockets gibt es m.E. noch keine .NET-Implementierung.

Es gibt für viele Protokolle im .NET-Framework keine Unterstützung und das ist gut so. Immerhin gibt es tausende verschiedene Protokolle in der Anwendungsschicht.

Der Threadtitel ist ein wenig irreführend, schließlich ist der klassische Handshake ein Begriff aus dem TCP-Protokoll.

Auch wenn es keine fertige .NET-Klasse gibt, die WebSockets beherrscht, so kann man die Implementierung jederzeit selbst vornehmen. WebSockets nutzt lediglich TCP. Es gibt für den Apache Server das Modul mod_pywebsocket.

BTW: Der Name WebSocket ist irgendwie selten doof gewählt. Man sollte lieber bei dem offiziellen Draft bleiben und das ganze auch so nennen, wie es gemeint ist. Es ist das Web Socket Protokoll. Das hat weder mit dem Web noch etwas mit Sockets zu tun.

Einen TCP-Server hab ich schonmal gecodet. Ich weis also wie so etwas zu funktionieren hat.

Wie bekomme ich das nun mit C# hin? Für alles was ich bisher mit TCP gemacht habe, musste ich mich nie um sowas kümmern.

Du verwendest hier ein nicht standardisiertes Protokoll, das wirst du also schon selbst mit dem Draft implementieren oder dir fertigen Code suchen müssen. TCP ist ein elementares Internettransportprotokoll. Das kannst du wohl kaum mit dem Web Socket Protokoll vergleichen. Und nur weil du einen TCP-Server "gecodet" hast, heißt du noch lange nicht das du weißt wie das TCP funktioniert.

Oder hast du dir zuvor das RFC 793 reingezogen? 😁

http://www.faqs.org/rfcs/rfc793.html

24.01.2010 - 03:04 Uhr

Steht doch in der Exception. Die IP-Adresse ist nicht gültig. Debugger anschmeißen, Codestelle identifizieren und Korrektheit der Adresse sicherstellen.

Letztens wollte einer einen TCP-Socket miteiner Broadcast IP-Adresse initialisieren. Wir hatten also schon alles, inklusive inkompatibler IPv4 zu IPv6 Adressen.

22.01.2010 - 12:07 Uhr

@Minz

Entspann dich, lehn dich in deinen Stuhl zurück und atme durch die Nase tief ein. Das hilft dir vielleicht dabei, wieder klar denken zu können.

Hier hat niemand irgendwelche Vorurteile geäußert, du hast mehrmals Hilfe erhalten mit Links und direkten Antworten.

Dein Problem wurde gelöst unter anderem mithilfe des von Stipo genannten Tutorials.

Ich habe keine Ahnung warum du hier abgehst, wie ein Zäpfchen. 8)

22.01.2010 - 11:11 Uhr

Hm das Tutorial sagt ich ich muss den Adresstyp explizit auf InterNetworkV6 ändern. Dann funktioniert allerdings der Laptop-Server nicht mehr

Bedeutet das nun dass die beiden Adresstypen nicht kompatibel sind und ich im Code abfragen muss, welcher Computer was verwendet?

Hat sich erledigt thx.

Siehst du, der Verweis von_ Stipo_ auf ein Tutorial war doch nicht verkehrt.

Es ist immer vorteilhaft sich mitden Grundlagen auseinander zu setzen, damit man auch weiß was überhaupt passiert.

Was eine Zeile so alles bewirken kann

Ja, und weil du gesehen hast was eine Zeile zum Thema Threading bewirken kann, kannst du auch einen Blick auf Multithreading in C# werfen. Dort steht alles, was du über Threads wissen musst/kannst.

😉

11.01.2010 - 13:52 Uhr

Broadcasts funktionieren nicht über das Internet!

Jetzt hab ich aber gesehen, dass die tcpClient Klasse selbst auch Methoden zum Empfangen hat.

tcpClient.GetStream();  

Aber da scheiterts jetzt. Da gibt er einen Netzwerkstream zurück?! Und ich finde auch keine Methode zum senden 😦

In Java hatte ich das Objekt in Bytes umgewandelt und verschickt. Aber das geht ja wahrscheinlich auch nur wieder mit diesem .. serialisieren (richtig?)
Könnt ihr mir einen Tip geben? Auch gerne einfach nur die richtigen Begriffe zum suchen.

Alle Objekte die du über TCP versendest müssen serialisiert werden, weil alles in 8-Bit großen Streams verschickt wird.

Das Objekt, also das Abbild der Klasse muss nach festen Kriterien in ein serialisiertes Schema konvertiert werden, welches dann beim Empfänger wieder deserialisiert werden kann.

Ansonsten kannst du dich hier mal einlesen.

http://www.codeplanet.eu/tutorials/csharp/4-tcp-ip-socket-programmierung-in-csharp.html

Da steht alles, was du wissen musst.

08.01.2010 - 14:42 Uhr

Wenn du richtig gelesen hast ist das ein Schulprojekt...!

Auch gut. Und warum muss es dann gleich ein Chat mit grafischer Oberfläche sein? Für einen Chat ist das nicht erforderlich und führt nur unnötigen Ballast bei der Netzwerkprogrammierung mit ein.

Sinnvoller wäre es, sich nur auf die Netzwerkprogrammierung mit einem einfachen Konsolenprogramm zu konzentrieren.

Wir haben nur die Grundkenntnisse wer weiß ob der uns alles beigebracht hat was wir brauchen.

Wo liegt der Unterschied zwischen TCP und UDP, was ist ein Socket, wie funktioniert ein BackgroundWorker und da du dich hier auf das erste Programm von Codeproject fokusierst, was sind Delegates und wie werden sie in dem Programm zusammen mit Ereignissen eingesetzt um Nachrichten asynchron abzuarbeiten. Wie sind die Nachrichten in dem besagten Programm überhaupt gestaltet, d.h. wie funktioniert das Anwendungsprotokoll, welches dort mit TCP realisiert wurde.

Ich denke es macht mehr Sinn, die Grundlagen solide zu erlernen, anstatt mit Programmen zu arbeiten, die man nur halbwegs begreift, um anschließend damit Eindruck zu machen.

Aber nun gut, so ist das nunmal...

08.01.2010 - 14:30 Uhr

evtl. solltest Du auf ein bestehendes projekt aufsetzen; z.B.
>

Was für einen Sinn macht es einen Chat schreiben zu wollen und dann auf ein fremdes, fertiges Projekt zurückzugreifen?

Noch dazu hat der Threadersteller Probleme mit den trivialsten Dingen, wie dem Ändern der IP-Adresse.

Leute, lernt doch erstmal die Basics, bevor ihr euch fremden Code zusammenklaut und dann euren Namen unter den Quellcode setzt.

😭

19.12.2009 - 20:58 Uhr

Der Junge hat weder Takt noch Verstand, beleidigt Leute und zitiert wie armer Schriftsteller.

Hat Jemand von Euch sinvolle Vorschläge, außer solche von ...

Unglaublich, was einem für Leute im Netz über den Weg laufen... man kommt sich vor, wie auf der Rütli-Schule.

19.12.2009 - 19:36 Uhr

Im Ernst:
Ich habe sockets schon vor 10 jahren programmiert...
Grundlagen habe ich durchaus, aber danke für die tipps.

Warum redest du dann von asynchronen Methoden und versuchst dein Programm krampfhaft mit Thread.Sleep(400) zum Laufen zu bringen, weil du nicht verstehst, warum dein Client ohne Sleep nicht alle Daten empfängt?

Das du schon vor 10 Jahren mit Sockets zu tun hattest, spricht nicht unbedingt für dich oder es ist eine dreiste Lüge. Du verstehst offensichtlich nicht, was TCP ist, geschweige denn, dass du das Protokoll vernünftig mit einem Socket nutzen könntest.

Ach so, Stefan:
wenn Du Dich damit so super auskennst, dann poste doch mal ein wernünftiges Beispiel...

Entweder bist du selten dämlich, oder dir fällt es schwer Hyperlinks anzuklicken. Such dir was aus.

Auf der bereits mehrfach genannten Seite

http://www.codeplanet.eu/tutorials/csharp/4-tcp-ip-socket-programmierung-in-csharp.html

sind Beispiele bis zum Abwinken genannt. Auch hier im Forum finden sich Client-Server-Demos.

Irgendwie kommt man sich hier verarscht vor, wenn man mehrfach Hilfestellung leistet und dann nur blöde Antworten erhält...

19.12.2009 - 16:33 Uhr

@Stefan:
anscheinend doch nicht,

Doch, doch.

ein Thread.Sleep ist notwendig um die Daten zu kriegen.

Nein. Du hast leider nur den TcpClient gelistet, aber das reicht aus um zu sehen was du falsch machst. Du versuchst mit dem NetworkStream zu schreiben und zu lesen, ohne TCP verstanden zu haben.

Die Daten werden nicht unmittelbar an die Gegenstelle versendet. Deine Gegenseite muss kontinuierlich in einer Schleife den TCP-Buffer auslesen, um an alle Daten zu gelangen. Der Empfänger muss wissen, welche Daten und wieviele Daten er empfangen wird. Du versuchst das Problem banal damit zu lösen, indem du Thread.Sleep(400) verwendest und hoffst darauf das Write alle Daten versendet hat und der Server antwortet bevor du mit Read einliest, aber das ist natürlich blanker Unsinn.

Du glaubst offensichtlich, dass das Senden und Empfangen der Daten unmittelbar und ohne Verzögerung vollständig geschieht, das ist natürlich grundlegend falsch.

Ich gehe davon aus
dass NetworkStream.BeginRead-Methode (System.Net.Sockets) / EndRead der Schlüssel zum Erfog ist.
Komme aber irgendwie nicht dahinter wie man es einsetzt..

Nö, das hat mit asynchronen Methoden gar nichts zu tun. Diese dienen lediglich dazu, den laufenden Thread nicht zu blockieren, solange Daten gesendet und empfangen werden.

Ich empfehle dir noch einmal dich dringend mit den Grundlagen auseinander zu setzen.

http://www.codeplanet.eu/tutorials/csharp/4-tcp-ip-socket-programmierung-in-csharp.html

Insbesondere Seite 2, dürfte bei dir für mehr Klarheit sorgen. Hier mal ein Teilsatz.

Paketsegmentierung

Ein einzelner Aufruf zum Senden von Daten über Send kann auch von der Gegenstelle in mehreren Receive-Aufrufen abgearbeitet werden.

[...]

Aus diesem Grunde wird in dem Beispiel kontinuierlich innerhalb einer Schleife die Methode Receive aufgerufen, wobei die Methode solange blockiert bis genügend Daten im TCP-Buffer zur Verfügung stehen um den allokierten Puffer zu füllen.

Dort findest du auch im Anhang komplette Beispiele für synchrone und asynchrone Socketaufrufe mit EndRead etc.

Lesen musst du den Artikel aber schon alleine, da kann dir keiner weiterhelfen.

19.12.2009 - 13:13 Uhr

Was heißt empfängt nicht den kompletten Datenstrom? Daten werden immerkomplett bei TCP empfangen, weil TCP ein sicheres Übertragungsprotokoll ist.

Zum Thema synchrone und asynchrone Bearbeitung, siehe

http://www.codeplanet.eu/tutorials/csharp/4-tcp-ip-socket-programmierung-in-csharp.html

17.12.2009 - 23:57 Uhr

Kann mir einer helfen?

Hier wird Ihnen geholfen.

TCP/IP Socket-Programmierung in C# (Client/Server Tutorial)

17.12.2009 - 02:56 Uhr

Das Problem scheint ja nicht zu sein das er nach dem eigentlich eintreffen der Nachricht weiter einliest sondern, dass der Stream nicht leer ist wenn er wieder versucht einzulesen. B.z.w das meine Schleife nicht alle Daten aus dem Stream holt oder Restdaten im Stream hängen bleiben.

Und genau deshalb habe ich dir geschildert, wie du die Daten aus dem TCP-Puffer lesen solltest!

Das Flush bei einem NetworkStream sinnlos ist, muss wohl nicht näher erklärt werden.

16.12.2009 - 19:36 Uhr

Hallo an alle Mitleser,

ich stehe vor der Frage wie man effizient eine Liste von Internetadressen abruft.

ThreadPool.QueueUserWorkItem ist effizienter.

Multithreading in C#

15.12.2009 - 12:38 Uhr

Natürlich empfängt man bei einem Stream-Socket (TCP) mit Receive weiter Daten. TCP kennt keine Nachrichtegrenzen, deshalb ist das auch ein Stream-Socket, d.h. ein Datenstrom!

Am einfachsten erledigst du das, indem du die Nachricht samt Nachrichtengröße überträgst.

Zum Beispiel:

15
Begrüßungsnachricht
28464
Daten

Auf der Empfangsseite liest du dann zuerst die Nachrichtenlänge, lädst dann mit Receive die nachfolgende Nachricht ein.

15.12.2009 - 03:10 Uhr

Woher soll das Framework wissen, welche Daten du da überträgst, wie diese kodiert sind und welche Delimiter du für deinen Text verwendest?

Du hast recht, generell ist das gar nicht klar, aber in meinem Fall, ist der Stream nicht anders aufgebaut, als ein FileStream bzw er wird nur ascii übertragen und den Delimiter \r\n und genau DESwegen hab ich gedacht, dass doch StreamReader eigentlich damit klarkomen müsste, denn dort funktioniert ReadLine() ja z.b auch anhand solcher Delimiter

Natürlich kannst du einen StreamReader verwenden, aber dann brauchst du dir auch keine eigenen Delimiter zu basteln, weil dann alles im StreamReader Format, sprich UTF-8 übertragen und kodiert wird. Wozu bastelst du also oben an irgendwelchen ASCII Kodierungen rum?

Dein Client macht dann:

TcpClient client = new TcpClient(server, servPort);
NetworkStream stream = client.GetStream();

StreamWriter writer = new StreamWriter(stream);

writer.WriteLine("Hallo Pumuckl!\n");
writer.Flush();

und dein Server liest in umgekehrter Reihenfolge mit dem StreamReader und readLine() aus. Ob du dabei direkt Sockets verwendest, oder die höheren Schichten TcpClient und TcpListener nimmst ist völlig wurscht.

// Listener instantiieren...
TcpClient client = listener.AcceptTcpClient();
StreamReader sr = new StreamReader(client.GetStream());

string data = sr.ReadLine();

Damit bist du an das Format des StreamReaders bzw. Writers gebunden.