2009-05-23 71 views
4

我正在編寫一個C#控制檯應用程序,它通過TCP連接到服務器,它使用單獨的線程來偵聽來自服務器的傳入消息,並且我希望它將它們寫入控制檯同時從控制檯讀取消息。我能夠做到這一點,但我有一個問題。C#控制檯:在讀取時寫入並保留結構

控制檯顯示此同時I型和消息進來:

味精從服務器
味精從服務器
我msmsg從服務器
克至服務器

而且我希望它將消息從服​​務器消息中分離出來,如下所示:

從服務器
味精

味精從服務器
味精從服務器
我味精服務器

如果我收到一條消息,我仍想保留我的輸入信息,但我不希望它與收到的消息混淆,我希望它在最後一行保持完整。

我可以那樣做嗎?如何?

當來自服務器的消息進來時,我可以將消息轉移到控制檯的末尾嗎?

+0

也許你可以告訴我們你當前的代碼的相關部分? – Noldorin 2009-05-23 17:18:39

+0

我不太明白你在問什麼,你能更明確嗎? – 2009-05-23 17:19:16

+0

我相信我知道你在做什麼,但我要說的是,如果我們不必在我們的答案中重寫大部分當前的方法,這將有所幫助。 – Noldorin 2009-05-23 17:21:04

回答

1

我相信這實際上可以使用標準的.NET控制檯API,使用一些hackery。你需要做的是創建一個異步的Read/ReadLine方法(我假設你已經完成了,根據你的帖子來判斷),並且一旦新數據到達,就允許它被取消。我假設你現在正在逐行發送輸入。對於「新的數據處理程序」中的僞可能是這樣的:

 
Save the current input buffer. 
Cancel the current asynchronous read. 
Reset the cursor position to the end of the last writing of new data. 
Output the new data. 
Save the cursor position. 
Restart the asynchronous read event. 

特別是,你需要更動Console.CursorLeftConsole.CursorTop性能。您可以通過直接與Win32 API控制檯函數接口來避免的某些問題,但它可能不值得費神。

希望有所幫助。

1

你不能直接通過C#中的BCL來做到這一點。雖然有兩個主要的選擇。

1)把它變成一個GUI應用程序,並有單獨的輸入/輸出區域。這是用戶POV中最「清晰」的選項,但需要GUI應用程序而不是控制檯應用程序。 2)P /直接調用console API。這使您可以逐點完全控制控制檯的視圖。請參閱SetConsoleCursorPosition和WriteConsole等。

+0

用於P/Invoke。 – 2009-05-23 17:22:47

+0

這個提議比這不提供什麼? http://msdn.microsoft.com/en-us/library/system.console_members(VS.80).aspx – 2009-05-23 17:24:11

1

您需要在某些object上使用lock,以便同時使用控制檯停止兩個線程。聲明是這樣的:

public static class ThreadSafeConsole 
{ 
    private static object _lockObject = new object(); 

    public static void WriteLine(string str) 
    { 
     lock (_lockObject) 
     { 
      Console.WriteLine(str); 
     } 
    } 
} 

現在叫ThreadSafeConsole.WriteLine而不是Console.WriteLine

0

如果我理解正確的話,你必須定義什麼開始,「打字安慰」的結局是你的應用程序,這樣你仍然可以在對象上鎖定,而正在發生的事情,而不是從插入郵件您的監聽器線程進入您輸入的文本。

public static Object consoleLock = new Object(); 
public static void Main(string[] args) 
{ 
    lock (consoleLock) 
    { 
     // now nothing can write to the console (if it's trying to lock onto it) 
     Console.WriteLine("Please Input Something"); 
     // read from console 
    } 
    // now, your separate thread CAN write to the console - without 
    // interrupting your input process 
}