|
Assumptions:
1) Local Intranet - non-public traffic
2) A single 'server' application will accept ISerializable objects from up to 25 different clients.
3) Objects are not sent at predetermined times (IE not on a timer) but by user interaction
I'm trying to figure out the best way to send objects over TCP. Lets say these objects range from 355 bytes all the way up to 69500 bytes.
Because we're dealing with 25 different clients I'd like this all done asyncronously.
Now, there's 2 ways I can think to do this.
1)
Asyncronously accept a Header class with an (int)size and a System.Type variables using Socket.BeginReceive(). In testing, this header class is about 300-400 bytes. On receipt of this object, create a byte array of the size indicated in the Header object. Then do a blocking .Receive() for the actual object.
On the clients, I'd first send this Header object over, followed immediatly by the actual object.
2)
Ignore the header class, just send over the entire object. On the server, use a buffer to concat say 1024 bytes at a time until the object does not fail a try/catch DeSerialize method.
I've got both ways working, #2 seems messy, because I'm relying on try/catch clauses. However, I've tried neither on a larger roll out. Is there perhaps a better way of doing this?
|
|
|
|
|
menzelAtPCA wrote: I'm trying to figure out the best way to send objects over TCP
No longer requires you writing socket code. There are other mechanisms like Web Service or Remoting.
menzelAtPCA wrote: A single 'server' application
The other mechanisms also afford using an application server rather than developing your own server application.
I have no idea if any of that interests you but there was no indication that you are aware of any of it.
led mike
|
|
|
|
|
I agree with led mike, Remoting and Web Services may accomplish the same goal without the need to write the low-level code yourself. Remoting even gives you the ability to remotely control an object. Also, you shouldn't really need to work with the underlying sockets, you should be able to use TcpClient and TcpListener to accomplish everything. If you decide to stay with the current route I'd recommend a protocol halfway between the two you proposed. I'd send a byte[] where the first 4 bytes represent a 32-bit integer that represents the length of the serialized data and the rest of the bytes in the array are the serialized object's data. If you are worried about data size you can compress the binary data before transmission and then decompress on the other end before unpacking the serialized object. Of course, the compression and decompression performance impact will need to be weighed against the reduction of size to determine if it is worth it.
Keep It Simple Stupid! (KISS)
|
|
|
|
|
At VC++ I've used the pretranslateMessage to change tab key by enter key to move between the controls. How to do it in c# windows form? thanks
|
|
|
|
|
You can handle KeyDown event of the form to move focus between controls. Make sure that you set KeyPreview property of the form to true.
|
|
|
|
|
How can I add a video in C# form. Can you help me please? Thanks in advance.
|
|
|
|
|
Open a form in your project, then right-click the ToolBox and pick Choose items... Click the COM tab and find Windows Media Player and check the box next to it. Click OK and then drag and drop a media player from the toolbox onto your form.
|
|
|
|
|
In C#:
So far I have set up a program so that it displays 16 random letters in random order at the beginning of my program. I am trying to get it so that these letters stay on top of the command prompt, and the input for the rest of the program stays below so that these letters can be read at any time. Any ideas as to how I can go about this?
I have tried recalling the letters but it displays a completely new random set of letters and I am trying to keep the same letters until I choose to reset them.
Thanks in advance.
|
|
|
|
|
SuperSken wrote: I have tried recalling the letters but it displays a completely new random set of letters and I am trying to keep the same letters until I choose to reset them.
You are probably "recalling" them by re-executing the function that gave them random letters in the first place. Try to store them in a string, and you can recall them (without modifications) whenever you want (until the GC removes the string from memory).
Perhaps you'd like to post your code (homework?) here, so we could take a look at it?
I are troll
|
|
|
|
|
So far I have this. I'm trying to get it so that when a word is added it either displays the letters again, or it just leaves the letters at the top and keeps the add word thing below and the command prompt doesn't scroll as such.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
Random rand = new Random();
string face;
string[] dice;
dice = new string[17]{"","-LRYTTE","-VTHRWE","-EGHWNE","-SEOTIS","-ANAEEG","-IDSYTT",
"-OATTOW","-MTOICU","-AFPKFS","-XLDERI","-HCPOAS","-ENSIEU",
"-YLDEVR","-ZNRNHL","-NMIQHU","-OBBAOJ"};
int letterOnDice;
int positionOfDice = 0;
Console.WriteLine(" _ _ _ _ _ _ _ _ _ _ _ _ _ _");
Console.WriteLine("| | | | |");
for (int i = 1; i <= 16; i++)
{
positionOfDice = rand.Next(1, 17);
while (dice[positionOfDice] == "")
{
positionOfDice = rand.Next(1, 17);
}
letterOnDice = (rand.Next(1, 7));
face = dice[positionOfDice].Substring(letterOnDice, 1);
Console.Write("| " + face + " ");
if (i == 4 || i == 8 || i == 12)
{
Console.WriteLine("|");
Console.WriteLine("| | | | |");
Console.WriteLine("|_ _ _ |_ _ _ |_ _ _ |_ _ _ |");
Console.WriteLine("| | | | |");
}
if (i == 16)
{
Console.WriteLine("|");
Console.WriteLine("| | | | |");
Console.WriteLine("|_ _ _ |_ _ _ |_ _ _ |_ _ _ |");
string[] inputText = new string[100000];
int addedWords = 0;
bool playAgain = true;
while (playAgain == true)
{
Console.WriteLine();
Console.WriteLine("What do you want to do?");
Console.WriteLine();
Console.WriteLine("1 - Add a word");
Console.WriteLine("4 - End");
Console.WriteLine();
Console.WriteLine();
string inputNumber = Console.ReadLine();
if (inputNumber == "1")
{
Console.WriteLine();
Console.WriteLine("Enter the word you wish to add: ");
inputText[addedWords] = Console.ReadLine();
addedWords++;
}
if (inputNumber == "4")
{
Console.WriteLine();
Console.WriteLine("Goodbye.");
Console.WriteLine();
playAgain = false;
}
}
}
}
}
}
}
|
|
|
|
|
How about a Console.Clear()? That resets the cursor's position to the upper-left corner. That would mean that you'll have to add code to write the old contents on the screen again.
I are troll
|
|
|
|
|
Hi,
Eddies idea of using the Console.Clear method and then rewriting the whole screen taking into account any changed data is the simplest way to go.
However if you want full control of the console then you need to learn about cursor positioning so you can place text at specific cooordinates. This example on msdn shows the general techniques http://msdn.microsoft.com/en-us/library/system.console.setbuffersize.aspx[^].
Generally people use a GUI for the type of effect that you want and I haven't formatted complex output on a console screen since about 1995. Have fun anyway!
Alan.
|
|
|
|
|
Hey i have two function fun1 and fun2...
fun1()
{
Console.WriteLine("Before Call of fun2");
fun2(9);
Console.WriteLine("After Call of fun2");
}
fun2(int a)
{
if(a<10)
return;
Console.WriteLine(a);
}
Now the question is that.when a<10 it returns, i want when a<10 it returns from fun2 as well as from fun1.
when a<10 Output should be
[Before Call of fun2]
Note that. there should not be any new variable in fun1.
is there any solutin for that..
thanks
|
|
|
|
|
hotthoughtguy wrote: is there any solutin for that..
No.
The only way to do this would be to move the "After call of fun2" message into the end of fun 2. Or duplicate the a<10 check in fun1 as well.
Simon
|
|
|
|
|
The best way that comes to mind to do this would be to make fun2 return a boolean. You could then check the return value in fun1 and continue or exit depending on the return value from fun2.
|
|
|
|
|
Hi,
instead of return, throw an exception and make sure you catch it where you want it to land.
|
|
|
|
|
Great Idea Luc Pattyn
thanks a lot. Your have solved my no of problems thanks again
|
|
|
|
|
you're welcome.
|
|
|
|
|
Go with Gideon not Luc.
Exceptions are for exceptional situations ie. events that you cannot control and would probably lead to the program halting. The one you describe is not exceptional i.e. it's one that depends on the logic of your code rather than something outside of it.
But then again I'm just an old fuddy-duddy who thinks that way.
|
|
|
|
|
Hi All,
Iam using FTPWebRequest for downloading the files...
Here, the function is working good. but while downloading the file, if the internet connection goes down, then this program going to throws the exception and end the process. So, in this scenario i want to pause/resume downloading...
How to acheive this...
If anybody knows help me...
thanks
Here my sample code
-------------------
public void Download(string fileName)
{
//Desc: To download the file from the ftp server
FtpWebRequest reqFTP;
try
{
//fileName = <<Name of the file to be createdNeed not name on FTP server. name name()>>
FileStream outputStream = new FileStream(downloadPath + "\\" + fileName, FileMode.Create);
reqFTP = (FtpWebRequest)FtpWebRequest.Create(new Uri("ftp://" + ftpServerIP + ftpPath + "/" + fileName));
reqFTP.Method = WebRequestMethods.Ftp.DownloadFile;
reqFTP.UseBinary = true;
reqFTP.Credentials = new NetworkCredential(ftpUserID, ftpPassword);
FtpWebResponse response = (FtpWebResponse)reqFTP.GetResponse();
Stream ftpStream = response.GetResponseStream();
long cl = response.ContentLength;
int bufferSize = 2048;
int readCount;
byte[] buffer = new byte[bufferSize];
readCount = ftpStream.Read(buffer, 0, bufferSize);
while (readCount > 0)
{
outputStream.Write(buffer, 0, readCount);
readCount = ftpStream.Read(buffer, 0, bufferSize);
}
reqFTP.Abort();
ftpStream.Close();
outputStream.Close();
response.Close();
}
catch (Exception ex)
{
Utils.Write(ex.Message);
}
}
Thanks & Regards
Kumaran
|
|
|
|
|
You can't pause and resume the download, but you can start a new download and start it from a certain point. Have a look at the ContentOffset property of the FtpWebRequest object. Also you can find examples of this just by Googling for "ftpwebrequest resume download".
|
|
|
|
|
I cant get it right... why this doesnt work :S:S
string b = "3.12312123";
if ((b[0] == '2' || b[0] == '3' || b[0] == '4' || b[0] == '5') && ((textBox2.Text != "703") || (textBox2.Text != "733")))
{
this.Text = "OK";
}
else
{
this.Text = "NOT OK!";
}
Any ideas?
Regards,
Matjaž
|
|
|
|
|
I can't be sure what you mean by not working, but that condition will always be true because of this:
((textBox2.Text != "703") || (textBox2.Text != "733"))
The textBox2 text will never be equal to both 703 and 733.
As an aside, you seem to be doing number comparisons, so I would recommend using number variables instead of strings. You could then test (b >= 2 && b < 6)
|
|
|
|
|
Okeeei...
So, i want to check... if its enetered only 703 or 733... BESIDES that the b starts with 2,3,4 or 5.
I really dont know how to make this thing to work... maybe i jsut have a bad day and am a bit confused... but yet again... i dont understand it
Please help? :/
Regards,
Matjaž
|
|
|
|
|
Matjaž Grahek wrote: i want to check... if its enetered only 703 or 733
I have no idea what the condition is.
a) Do you want this.text = "OK" if text = 703 or 733?
b) or do you want this.text = "Not Ok!" if text = 703 or 733?
int textVal = 0;
int.tryparse(textbox2.text, out textVal);
if(textVal == 703 || textVal==733)
{
this.Text = "ok";
this.Text = "Not Ok";
}
Matjaž Grahek wrote: b starts with 2,3,4 or 5
here is a simple solution to that:
int val = 0;
int.tryparse(b[0].ToString(), out val)
this should help,
Prateek
|
|
|
|