C#與NDde-如何連結超級大三元

續前文(台証超級大三元DDE)從Excel中找到需要的項目運算式,接著便是用C#與NDde去連結那些項目,以下就Visual C# 2008 Express為開發工具記錄作法。

0. 先啟動並登入台証超級大三元
登入台証超級大三元

1. 開啟新專案Windows Form應用程式
Windows Form應用程式

2. 在右邊方案總管的參考上按右鍵選加入參考
加入參考

3. 瀏覽到下載NDde的路徑,撰擇NDde.dll
NDde.dll

4. 從左邊工具箱中拉三個Label到Form1裡
拉三個Label到Form1

5. 在右邊方案總管的Form1.cs上按右鍵選檢視程式碼
檢視程式碼

6. 最後複製並貼上下述範例代碼

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using NDde.Client;

namespace WindowsFormsApplication1
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();

            //超級大三元每一個item都需要建立一個DDE連結,所以用陣列的方式建了三個
            //如何找到大三元的連結參數TS及KS就不贅述了,請自行參閱blog文(台証超級大三元DDE)
            DdeClient[] ddecon = new DdeClient[3] { new DdeClient("TS", "KS"), new DdeClient("TS", "KS"), new DdeClient("TS", "KS") };
        
            for (int i=0;i<3;i++)
            {
                try
                {
                    ddecon[i].Connect();
                }
                catch (Exception e) { MessageBox.Show(e.ToString()); }
            }

            //連結並關注item,以下item分別表示時間、成交價及單量
            //如何找到TXFL9.123等連結參數就不贅述了,請自行參閱blog文(台証超級大三元DDE)
            ddecon[0].StartAdvise("TXFL9.123", 1, true, 60000);
            ddecon[0].Advise += OnAdvise;

            ddecon[1].StartAdvise("TXFL9.124", 1, true, 60000);
            ddecon[1].Advise += OnAdvise;

            ddecon[2].StartAdvise("TXFL9.128", 1, true, 60000);
            ddecon[2].Advise += OnAdvise;
        }

        private void OnAdvise(object sender, DdeAdviseEventArgs args)
        {
            //如果NDde有通知參數值有異動,就更改label值
            if (args.Item == "TXFL9.123") myUI(args.Text, label1);
            else if (args.Item == "TXFL9.124") myUI(args.Text, label2);
            else if (args.Item == "TXFL9.128") myUI(args.Text, label3);
        }

        //Form上變更Text函數,請參閱http://www.dotblogs.com.tw/yc421206/archive/2009/02/13/7141.aspx
        private delegate void myUICallBack(string myStr, Control ctl);
        private void myUI(string myStr, Control ctl)
        {
            if (this.InvokeRequired)
            {
                myUICallBack myUpdate = new myUICallBack(myUI);
                this.Invoke(myUpdate, myStr, ctl);
            }
            else
            {
                ctl.Text = myStr;
            }
        }
    }
}

7. 執行結果
執行結果

註1:記得下載NDde並解壓縮
註2:此範例可從這裡下載原始碼

您可能也會喜歡…

10 個回應

  1. Kenming Wang表示:

    Hi, 請記得 “Keep” 住 Dde Connection,也就是要能保持為 “Stateful” 狀態喔。 🙂

  2. ANDY表示:

    …我剛設了一個按鈕,去測每個連結的是否IsConnected,都回傳為True,過十分鐘去押也一樣為True,應該表示都一直有在連線,也能用該連線再去StartAdvise其它item並取得資料,就我的觀點是有維持住Dde Connection了…

    但您的意思,似乎還有其它動作要做才算keep住Dde Connection?
    煩請指導,感謝

  3. Kenming Wang表示:

    思考一下,DdeClient[] 這個 Array 有確實被 Form1 給 Keep 住嗎?
    從你上述列出的 partial 程式碼, I don’t think so….

    是否這些 DDe connection instances 在過程中有被系統 GC(Garbage Collection) 掉了呢?

    看你的寫法,好像都是偏向 Form-based 的程序性寫作,建議還是要有物件的基本思維邏輯,這樣比較容易懂得物件與物件之間的訊息溝通,以及物件的生命週期觀念。

  4. ANDY表示:

    呃,上述程式碼是簡單的範例供使用者參考,所以並沒有想那麼多…

    在原本的實作上,我是另外寫成物件去call的,因為還要同時連結其它券商的DDE server,所以寫成物件會比較方便…

    但您提到的重點,物件生命週期及GC,確實是我沒有去研究的地方…
    感謝您的留言指導^^

  5. ANDY表示:

    先不論我原本失敗的實作,我剛搜尋了一下,在C#中,陣列即是物件,該物件若有被持續參考使用到,就不會有GC的問題(至少以往我在java寫作程式時是這樣,雖然沒碰它的UI)…

    但您留言重點好像是落在Form本身是否有在keep物件…

    註:使用本文範例,可能是今日期貨成交量不高的關係,所以數字很順地一直在跳動,沒有發生您說的GC或是DDE connection可能遺失的問題…

  6. Kenming Wang表示:

    應該是這樣吧:

    private DdeClient[] ddecon;
    public Form1()
    {
    ddecon = new DdeClient[3] { …….}
    }

    這個宣告是要在放在 Class-level,而不是在 constructor 內宣告才是。

    這也是我一再提醒, Form1 與 dde connection,生命週期一定要相等的意思。 否則,系統哪時候 GC 回收,都說不定的。

    看看是否這樣。 若還有問題,可以 Email 給我。

  7. ANDY表示:

    嗯,我了解您的意思了…

    我原本的實作DdeClient的確是放在Form1外,這個範例比較偷懶沒去注意那麼多…^^”

    只是,看來仍無法解決我之前做白工的問題T_T

    題外話,C#我是不熟,上述範例以資深程式設計的角度來講,確實不夠工整,但我覺得除非關掉Form1,那麼系統沒道理會去對Form1做GC回收,畢竟Form1是使用者一直在執行的介面,如果我不定時的要用到Form1物件做些事情怎麼辦?

    所以就本文範例來講,關掉Form1等於是關掉DDE connection,生命週期是相等的…(範例沒個人家寫好還狡辯^^”,請笑笑看看這段話就好)

    很高興您能撥空與我交流,日後有問題再至您blog打擾^^

  8. akai表示:

    首先感謝您的程式碼 受益良多

    我個人不喜歡用.StartAdvise這個方法 我有些功能需要把DDE關掉 重新叫起會有delay 有時後還會當掉

    我之前引用日盛的DDE 都是用.Request這個方法 需要再去抓 抓日盛的DDE資料都沒問題 抓凱基的就抓不到了 請問版大有什麼辦法可以克服嗎?

    感謝

  9. 認真想學C#表示:

    請問 DDE 連線後 , 報價顯示後並劃出一個走勢圖或一分K棒圖怎樣寫?

  10. 認真想學C#表示:

    為什麼使用你的程式碼,我改為康和連結DDE後 報價都會延遲出來,有時候只有2個報價,查了好多遍?不知道出在哪裡?

發佈留言

發佈留言必須填寫的電子郵件地址不會公開。 必填欄位標示為 *