2015年12月30日 星期三

[VS 2013] 找出複雜程式碼

    前言 : 利用vs幫自己找出需要重構的複雜程式碼

     

    這邊有一五項指標給大家做參考 :
    a.循環複雜度(Cyclomatic Complexity) :   <10

    b.繼承深度 :  <3
                 ex . 抽象類別 –>  衍生1 –>  衍生2
    c.類別結合程度(Class Coupling)
    d.程式碼行數 :  一個function < 40
    e.可維護性 : 官方建議 > 20 是高維護性


    步驟 :


    1. 點擊分析 –> 計算方案的程式碼度量


    2015-12-30_112449

    2. 等待分析完成
    2015-12-30_112559

    3. 篩選器 : 選擇循環複雜度 最小20 (可自行調整)並確定
    2015-12-30_112920

    4. 匯出Excel
    2015-12-30_112654
    5. Excel 表格中第一欄就會顯示各層級,我們只篩選”成員”
    2015-12-30_112957



    6. 登登登-結果出爐,接下來我們就可以自行判斷裡面哪些是需要重構的程式碼囉2015-12-30_113125

參考 :

 [Tool]Visual Studio 2010 - 程式碼度量
Visual Studio 計算程式碼度量 - Code Metrics Viewer 2013


2015年12月29日 星期二

[C#] 兩個問號??

var demo = value ?? 0;

就是判斷value 是否為null, 如果是null則賦予0值

就是語法糖 :  var demo = (value != null) ? value :  0;

[Error][IIS][php] 處理常式 "PHP_via_FastCGI" 的模組清單中有錯誤的模組 "FastCgiModule"

錯誤訊息 :

2015-12-29_091359

解釋 :

最有可能原因提到為安裝完整ASP.NET,因此到WINDOWS 功能確認是否都有開啟開發功能

如下圖,都開啟後就順利在iis使用php 網站囉

 

2015-12-29_091659

2015年12月25日 星期五

[C#] 變異性

變異性

  • 共變性
    • 用基底類別取代衍生類別
    • 常用在輸出用
    • 多用再回傳
  • 不變性
    • 如 泛型類別具不變性
  • 逆變性
    • 用衍生類別取代基底類別
    • 多用在傳進參數
Tips
  1. 先寫共變性
  2. 再去分辨
泛型介面變異性

        宣告Out
            共變性
                IEnumerable<T>
        宣告In
            逆變性
                IComparer<T>

[C#] 泛型

筆記整理

  • .Net2.0 開始
  • 強型別概念
  • 應用 : 介面、類型、方法、委派
  • 泛型會實做非泛型
  • 避免容器操作Boxingm Unboxing

default 關鍵字

  • 當沒有條件約束時 : return default(T)
  • 當有條件約束時 : 
    • 實質型別 : 0
    • 參考型別  : null
  • 泛型約束條件
    • where T :  Class
    • where T : new()   ----- 必須擁有共用的無參數建構函示

[C#] 介面 Interface

介紹

  • 抽象中的抽象
  • 職責範圍小設計必須要小(設計必須要小)

筆記整理

  • 關鍵字使用interface
  • 界面是屬性、方法、事件、索引的簽章
  • 不能定義執行個體欄位與建構式
  • 不允許定義靜態成員
  • 繼承同名簽章的多介面需要”明確實做”!
    • 明確實做需要轉型才能呼叫

[C#] 擴充方法

筆記整理

  • Class 前需要加 Static
  • 所有Method 前也需要加 Static
  • 編譯後就是static method
  • 不能與原類別方法同名
  • 講求內聚性的方法一定要用成員方法

好處

  • 提高閱讀性
  • 現在常大量使用linq (ex. abc.where(…)),如果沿用靜態方法就會變成大腸包小腸

使用情境

  • 遇到 seal class
  • 類別不該用繼承做的時候-造成低內聚、高耦合

2015年12月24日 星期四

[MVC] 使用ActionFilterAttribute 紀錄Log

假設當Client發出一個搜尋的Request,我們希望可以在紀錄使用者搜尋的關鍵字,以便日後可以統計…

這個需求就可以利用ActionFilterAttribute來完成,首先先看下面進如Action的簡易流程示意圖 :


圖片出處

2015年12月18日 星期五

[C#][MVC] Facebook OAuth 驗證與登入

1. 申請自己的app : https://developers.facebook.com/apps/




 





2. 選擇要建立的app (範例網站)

3. 輸入app名稱

4. 選擇你的類型後, 點擊新增


























5. 看到此頁面就是成功了申請囉, 然後照著步驟走
5.1 記得設定你的網站網址 : ex. http://localhost:7115/




6. 回到 https://developers.facebook.com/apps/ 選擇TestWeb
7. 記住你的App ID
8. 在你的網站js輸入以下code (請自行重構)


// For FB
window.fbAsyncInit = function() {
    FB.init({
        appId: xxxxxx// App ID
        status     : true, // check login status
        cookie     : true, // enable cookies to allow the server to access the session
        xfbml: true,  // parse XFBML
        version: 'v2.5'
    });

    // Additional initialization code here
    FB.Event.subscribe('auth.authResponseChange', function (response) {
        if (response.status === 'connected') {
            // the user is logged in and has authenticated your
            // app, and response.authResponse supplies
            // the user's ID, a valid access token, a signed
            // request, and the time the access token
            // and signed request each expire
            var uid = response.authResponse.userID;
            var accessToken = response.authResponse.accessToken;
            var data = {
                token: accessToken
            }
            // TODO: Handle the access token
            console.log(uid);
            console.log(accessToken);
            ajaxServer('Home/FacebookLogin', data);
        } else if (response.status === 'not_authorized') {
            // the user is logged in to Facebook,
            // but has not authenticated your app
        } else {
            // the user isn't logged in to Facebook.
        }
    });
};

function fbLogout() {
    FB.logout(function (response) {
        window.location.reload();
        // user is now logged out
    });
}

// Load the SDK Asynchronously
(function(d){
    var js, id = 'facebook-jssdk', ref = d.getElementsByTagName('script')[0];
    if (d.getElementById(id)) {return;}
    js = d.createElement('script'); js.id = id; js.async = true;
    js.src = "//connect.facebook.net/en_US/all.js";
    ref.parentNode.insertBefore(js, ref);

}(document));

function ajaxServer(url, data) {
    $.ajax({
        url: url,
        data: data,
        type: "POST",
        dataType: 'json',
        success: function (msg) {
            console.log(msg);
        },

        error: function (xhr, ajaxOptions, thrownError) {
            alert(xhr.status);
            alert(thrownError);
        }
    });
}

註.裡面的ajax 就是post到你的server, 

9. 至html頁面放入以下 :
<div class="fb-login-button" scope="public_profile,email" data-show-faces="true" data-width="400" data-max-rows="1"></div>
<a href="#" onclick="fbLogout();">FB Sign out</a>
<div id="fb-root"></div>
標籤scope就是你希望請求的資訊,可參考此 : https://developers.facebook.com/docs/facebook-login/permissions#reference


9.  server端(.net), 請到nuget 下載facebook套件  http://facebooksdk.net/docs/web/getting-started/

10. 寫一個Action :

        [HttpPost]
        public JsonResult FacebookLogin(string token)
        {
            var client = new FacebookClient(token);
            dynamic result = client.Get("me", new { fields = "name,id,email" });
            string name = result.name;
            string id = result.id;
            return Json(name, JsonRequestBehavior.AllowGet);
        }


2015年12月16日 星期三

2015年12月12日 星期六

[Error] Missing type map configuration or unsupported mapping

遇到 Missing type map configuration or unsupported mapping...

表示automapper 沒有實做此model間的轉換

請實做Mapper.CreateMap<xxx, yyy>();


2015年12月11日 星期五

[Error] 佈版 出現Mapping types: DbQuery.......錯誤


如圖 :

 

問題其實很單純= =+

他主要是說找不到對應欄位,所以去檢查db欄位是不是有少加欄位!!

[Error] LayoutRender cannot be found: ‘aspnet-sessionid’




原因 : 沒有加入nlog.web參考,用nuget重新加入即可

2015年12月10日 星期四

[Error] RouteConfig 設定縮圖位置但依舊無法顯示

routes.MapRoute(                 name: "ImgRoute",                 url: "imgs/{Type}/{width}/{height}/{*imgPath}",                 defaults: new { controller = "FileUtil", action = "Img", id = UrlParameter.Optional }             );

但是輸入圖片網址後卻出現


2015-12-10_111031


解決方法 :


webconfig 加上 :

<modules runAllManagedModulesForAllRequests="true">

2015年12月8日 星期二

[Error] 無法載入檔案或組件 'Newtonsoft.Json' 或其相依性的其中之一。 找到的組件資訊清單定義與組件參考不符。 (發生例外狀況於 HRESULT: 0x80131040)

你是否也有遇到下面問題

無法載入檔案或組件 'Newtonsoft.Json' 或其相依性的其中之一。 找到的組件資訊清單定義與組件參考不符。 (發生例外狀況於 HRESULT: 0x80131040)

2015-12-08_170401

原因:各專案的Newtonsoft.Json版本不同,直接去nuget管理統一更新版本即可!!

[Error][mvc] The configuration section 'autofac' could not be read.

2015-12-08_101008

忘記設定webconfig autofac 區塊囉 !!

1. 僅示意

    <section name="autofac" type="Autofac.Configuration.SectionHandler, Autofac.Configuration" />

2.僅示意

<autofac>     <modules>       <module type="ServiceModule, BLL.Modules" />         </modules>     <components>       <component type="Utility.Extensions.NLOG.LogRequestAttribute, OI.Utility.Extensions" service="Utility.Extensions.NLOG.LogRequestAttribute, Utility.Extensions" />     </components>   </autofac>

[Error] entity framework循環參考

2015-12-07_174812

之前已經有寫過了,只是還是滿常遇到的(可參考之前的文章)

這次的錯誤似乎跟循環參考沒啥關係,但是看到上面框起來的物件就是ef proxy的物件!!

所以只要把循環參考的property標記[JsonIgnore]即可

2015年12月6日 星期日

[C#] 靜態類別

靜態類別

  • 一定是密封,無法被繼承
  • 無法產生實體
  • 只包含靜態成員
  • 無法控制靜態建構涵式執行時間

使用時機

  • 從設計的角度思考
    • 內聚性高的一定是執行個體成員
    • 內聚性低的靜態成員佳 (ex.util)

[C#] 類別&類別成員

存取修飾詞

  • public : 公開
  • private : 私人
  • protected : 繼承者可以存取
  • internal : 組件內可存取
  • internal protected : 兩者取其一

其他修飾詞

  • abstract
    • 只有簽章
    • 一定要override –> 強迫實作
    • 使用情境:職責很抽象無法預定(ex."打"架、”打”屁、”打”牌)
  • virtual : 可以覆寫
  • sealed
    • 不可被繼承
    • 常配override使用
  • new
    • 少用,最好不用!!!
    • 上層沒有修飾詞,要蓋過去時才用
    • 重要 :  使用new的method會靠type的型別來執行該method(慎用)
  • override : 追回最上層一定是abstract、virtual,override本身也可以被覆寫

型別物件vs值型個體物件

常數

  • 編譯時期就會嘗試取代值
  • 使用readonly property取代

欄位(field)

  • 類別層級的變數
  • 很少是public

屬性(property)

  • 一種方法的變形
  • 自動實作屬性 ({get;set;})
  • 編譯完是沒有屬性的
  • 唯讀/寫 (ex. {get;private set;})

方法(method)

  • 關鍵字 : ref、out、params
    • ref : 遞迴較常用,防止stack爆掉
    • out : 強迫該方法一定要產生該物件
    • params : 語法糖
  • 傳值與傳址 : 分實體與參考型別的傳值、址,主要主詞在變數就對了
  • Tuple
  • object x; 代表 ?? (0000, null)
  • 多載 :
    • 逼不得已才用(東西一多就會變複雜)
    • 如果參數一樣多 : 使用泛型、繼承式多型

委派

  • 基礎 :
    • 參考型別
    • 一種方法簽章的型別
    • 透過Invoke叫用,依序執行所有linkedlist
    • 心中都有一個linkedlist
  • Action型別
  • Func型別
  • Predicate(舊)

事件

  • 觀察者模式簡化版
  • mvc比較少用到

建構式

  • 呼叫自己的建構式很重要
  • 隱含 : 語法糖,你應該要寫但你不寫也沒關係
  • 建構式不會被繼承
  • 繼承鏈順序
    •    繼承關係 : System.Object -> A –> B
    •    GO :  B初始分配位置 -> A初始 -> OBJ初始 -> A建構 -> B建構

[C#] 型別與變數

型別概論 :

  • Primitive Type
  • Value Type
    •     結構
    •     列舉
  • Reference Type
    •     介面
    •     類別
    •     委派

參考型別 vs 實值型別:

  • 記憶體分類的角度 :
    • 實值行別存在stack
    • 參考型別存在Heap
  • 變數觀點 :
    • 實值型別變數就是物件本身
    • 參考型別變數則是儲存指向物件的參考(位址)

var 宣告:

  • 強型別
  • 只能做為區域變數使用

衍伸觀念:

  • 參考型別執行個體與變數的關係
  • 參考型別執行各體(物件)的型別和變數一定要相同?

boxing & unboxing :

  • boxing : value type轉成reference type
  • unboxing : 反之

[C#] 繼承、封裝、多型

記住 : 絕大部分的設計就是在好好運用這三大特性!!!

最重要的 : 多型

 

繼承:

  • 擁有被繼承者的型別特徵
  • 只能繼承一個父類別(祖父以上…不算)
  • 可實作多個介面

封裝:

  • 隱藏不讓外界所知資訊與行為
  • 透過特定的公開介面與外界互動

多型:

  • 繼承式多型 (ex. base(),實作介面)
  • 參數式多型 (泛型)
  • 多載 (相同名稱,不同參數清單)
  • 強制同型(ex.轉型)

[C#] 物件、類別、抽象化

物件 :

  1. 外界真實人事物的抽象定義
  2. 程序和資料的結合

類別 :

  1. 透過分類將一群類似的物件”抽象化”的概念

抽象化:

  1. 分類的基礎技巧
  2. 找出關鍵性的特徵加以描述,ex.球的分類可以是顏色或球的種類等
  3. 例如 : 地圖

[C#] OOP 物件導向學習(簡介)

前言 : …一次學七個語言,不如一個語言學七次,重新複習C#。

章節 :

1. 物件、類別、抽象化

2. OOP三大特性

3.型別與變數

4.類別&類別成員

5.靜態類別

 

OOP by C#

2015年12月4日 星期五

[C#] vs2013 建立自己的windowservice

1.使用vs 2013 , 請先至擴充搜尋 "Visual Studio Installer" 下載”安裝專案”

2015-12-04_132231

2. 開始建立第一個windowservice

2015-12-04_112305

3. service.cs 生成後,在工具箱放一個eventLog

2015-12-04_1125082015-12-04_112548

4. 按f7 進入code behind, 撰寫程式

2015-12-04_112617

5.完成後加入安裝程式

2015-12-04_1127132015-12-04_112726

6.針對安裝程式設定屬性(兩個都要設唷)

2015-12-04_1128042015-12-04_113001

7.此為最一開始擴充套件的安裝專案擴充,新增安裝專案

2015-12-04_113041

照圖設定

2015-12-04_1131252015-12-04_113150

2015-12-04_1132092015-12-04_113230

*選擇剛剛的window service

2015-12-04_113332

一直確定後,生成四個動作

2015-12-04_113349

重新建置

2015-12-04_113421

安裝

2015-12-04_113438

照著步驟安裝後,即可到服務去啟動它

2015-12-04_113542

eventlog也可以到事件檢視器查看(控制台->系統及安全性->系統管理工具)

2015-12-04_114707

2015年12月3日 星期四

[MVC][Error] js date物件無法 於mvc model binding

今天遇到一個很見鬼卻有很簡單的問題,
當使用js post時間欄位至server時,mvc 會有model binding幫我們做好繫結,變成強行別的DateTime,
但今天因為使用get方法,以及在query string串接js的date 物件,卻發現到server時欄位一直binding不起來,
最後發現如果是用query string 串接在轉換時會變成其他編碼,難怪mvc會看不懂 XD
範例如下 :

var a = new Date();

console.log(a);

//Thu Dec 03 2015 19:19:16 GMT+0800 (台北標準時間)
//實際http get : ?Thu%20Dec%2003%202015%2019:18:29%20GMT+0800%20(台北標準時間)



因此要就要自己轉換一下時間或是先編碼escape(Date);