11步让你成为更优秀的程序员 各种技巧

1.永远不要复制代码



不惜任何代价避免重复的代码。如果一个常用的代码片段出现在了程序中的几个不同地方,重构它,把它放到一个自己的函数里。重复的代码会导致你的同事在读你的代码时产生困惑。而重复的代码如果在一个地方修改,在另外一个地方忘记修改,就会产生到处是bug,它还会使你的代码体积变得臃肿。现代的编程语言提供了很好的方法来解决这些问题,例如,下面这个问题在以前很难解决,而如今使用lambdas却很好实现:






现在我们重构含有部分相同代码的函数,用delegate模式重写它们:






2. 留意你开始分心的时候



当你发现自己在浏览facebook或微博、而不是在解决问题,这通常是一种你需要短暂休息的信号。离开办公桌,去喝一杯咖啡,或去跟同事聊5分钟。尽管这样做看起来有点反直觉,但长久去看,它会提高你的工作效率。



3. 不要匆忙赶任务而放弃原则



当带着压力去解决一个问题或修改一个bug,你很容易失去自制,发现自己匆匆忙忙,甚至完全忘了一直坚持的重要的测试过程。这通常会导致更多的问题,会让你在老板或同事眼里显得很不专业。



4. 测试你完成的代码



你知道你的代码能做什么,而且试了一下,它确实好用,但你实际上需要充分的验证它。分析所有可能的边界情况,测试在所有可能的条件下它都能如期的工作。如果有参数,传递一些预期范围外的值。传递一个null值。如果可能,让同事看看你的代码,问他们能否弄坏它。单元测试是到达这种目的的常规方法。



5. 代码审查



提交你的代码之前,找个同事一起坐下来,向他解释你做了哪些修改。通常,这样做的过程中你就能发现代码中的错误,而不需要同事说一句话。这比自己审查自己的代码要有效的多得多。



6. 让代码更少



如果你发现写了大量的代码来解决一个简单的问题,你很可能做错了。下面的boolean用法是一个很好的例子:






这时你应该写成这样:






代码越少越好。这会使bug更少,重构可能性更小,出错的几率更小。要适度。可读性同等重要,你可不能这样做而使代码丧失可读性。



7. 为优雅的代码而努力



优雅的代码非常的易读,只用手边很少的代码、让机器做很少的运算就能解决问题。在各种环境中都做到代码优雅是很难的,但经过一段时间的编程,你会对优雅的代码是个什么样子有个初步的感觉。优雅的代码不会通过重构来获得。当你看到优雅的代码是会很高兴。你会为它自豪。例如,下面就是一个我认为是优雅的方式来计算多边形面积的方法:






8. 编写不言自明的代码



勿庸置疑,注释是编程中很重要的一部分,但能够不言自明的代码跟胜一筹,因为它能让你在看代码时就能理解它。函数名变量名要慎重选择,好的变量/方法名字放到语言语义环境中时,不懂编程的人都能看懂。例如:






能自我说明的代码不能代替注释。注释是用来解释“为什么”的,而自我说明的代码是来描述“是什么”的。



9. 不要使用纯数字



直接把数字嵌入代码中是一种恶习,因为无法说明它们是代表什么的。当有重复时更糟糕——相同的数字在代码的多个地方出现。如果只修改了一个,而忘记了其它的。这就导致bug。一定要用一个命名常量来代表你要表达的数字,即使它在代码里只出现一次。



10. 不要做手工劳动



当做一系列动作时,人类总是喜欢犯错误。如果你在做部署工作,并且不是一步能完成的,那你就是在做错事。尽量的让工作能自动化的完成,减少人为错误。当做工作量很大的任务时,这尤其重要。



11. 避免过早优化


当你要去优化一个已经好用的功能代码时,你很有可能会改坏它。优化只能发生在有性能分析报告指示需要优化的时候,通常是在一个项目开发的最后阶段。性能分析之前的优化活动纯属浪费时间,并且会导致bug出现。


来源:http://www.manew.com/thread-47665-1-1.html


new 发布于 2016-3-1 01:50

Unity A*寻路 C# Unity游戏研究

首先看了这篇翻译外国人的文章http://www.raywenderlich.com/zh-hans/21503/a%E6%98%9F%E5%AF%BB%E8%B7%AF%E7%AE%97%E6%B3%95%E4%BB%8B%E7%BB%8D



1.定义地图节点,及初始化地图数据

using UnityEngine;
using System.Collections.Generic;

public class Map
{
    /// <summary>
    /// 初始化地图
    /// </summary>
    /// <returns></returns>
    public static Dictionary<string, MapInfo> GetMap()
    {
        Dictionary<string, MapInfo> temp = new Dictionary<string, MapInfo>();

        for (int i = 0; i < 10; i++)
        {
            string s = "";
            for (int j = 0; j < 10; j++)
            {
                int tt = 0;
                if (i > 1 && i < 8 && j == 5)
                {
                    tt = 1;
                }
                MapInfo mi = new MapInfo(i, j, tt);
                temp.Add(i + "-" + j, mi);
                s += mi.tag + " ";
            }
            Debug.Log(s);
        }
        return temp;
    }
}

/// <summary>
/// 地图节点
/// </summary>
public class MapInfo
{
    /// <summary>
    /// X
    /// </summary>
    public int x;
    /// <summary>
    /// Y
    /// </summary>
    public int y;
    /// <summary>
    /// 是否可行走
    /// </summary>
    public int tag;
    /// <summary>
    /// G
    /// </summary>
    public int gValue;
    /// <summary>
    /// H
    /// </summary>
    public int hValue;
    /// <summary>
    /// 父节点
    /// </summary>
    public MapInfo parent;

    public MapInfo()
    { }

    /// <summary>
    /// 构造
    /// </summary>
    /// <param name="x"></param>
    /// <param name="y"></param>
    /// <param name="tag"></param>
    public MapInfo(int x, int y,int tag)
    {
        this.x = x;
        this.y = y;
        this.tag = tag;
        this.gValue = 0;
        this.hValue = 0;
        this.parent = null;
    }
}

2.由起点终点寻路,有注释,知道原理的话,应该很容易懂

using UnityEngine;
using System.Collections.Generic;

public class AStar : MonoBehaviour
{
    /// <summary>
    /// 地图
    /// </summary>
    Dictionary<string, MapInfo> map;
    /// <summary>
    /// open列表
    /// </summary>
    Dictionary<string, MapInfo> openList = new Dictionary<string, MapInfo>();
    /// <summary>
    /// close列表
    /// </summary>
    Dictionary<string, MapInfo> closeList = new Dictionary<string, MapInfo>();

    /// <summary>
    /// 当前点
    /// </summary>
    MapInfo currentV;
    /// <summary>
    /// 当前点的相邻节点列表
    /// </summary>
    Dictionary<string, MapInfo> adjancentMap;

    // Use this for initialization
    void Start () 
    {
        map = Map.GetMap();
        MapInfo st = map["5-2"];//start
        MapInfo end = map["6-8"];//end

        FindPath(st, end);
    }

    /// <summary>
    /// 寻路
    /// </summary>
    /// <param name="start">起点</param>
    /// <param name="end">终点</param>
    public void FindPath(MapInfo start,MapInfo end)
    {
        openList.Add(start.x + "-" + start.y, start);

        do
        {
            currentV = GetTheLowestFrom(openList);

            closeList.Add(currentV.x + "-" + currentV.y, currentV);
            openList.Remove(currentV.x + "-" + currentV.y);

            if (closeList.ContainsKey(end.x + "-" + end.y))
            {
                Debug.Log("FindPath");

                PrintThePath(end);
                break;
            }

            adjancentMap = AdjacentList(currentV);

            foreach (string k in adjancentMap.Keys)
            {
                if (closeList.ContainsKey(k))
                {
                    continue;
                }

                if (!openList.ContainsKey(k))
                {
                    adjancentMap[k].parent = currentV;
                    adjancentMap[k].gValue = currentV.gValue + 1;
                    adjancentMap[k].hValue = GetManhattanDistance(adjancentMap[k], end);
                    openList.Add(k, adjancentMap[k]);
                }
                else
                {
                    int g = currentV.gValue + 1;
                    if (g < adjancentMap[k].gValue)
                    {
                        adjancentMap[k].gValue = g;
                        adjancentMap[k].parent = currentV;
                    }
                }
            }

        } while (openList.Count > 0);
    }

    /// <summary>
    /// 获取openlist中F最小的节点
    /// </summary>
    /// <param name="open"></param>
    /// <returns></returns>
    public MapInfo GetTheLowestFrom(Dictionary<string, MapInfo> open)
    {
        MapInfo result=null;
        int min = 10000;
        foreach (MapInfo m in open.Values)
        {
            if (m.gValue + m.hValue < min)
            {
                result = m;
                min = m.gValue + m.hValue;
            }
        }
        return result;
    }

    /// <summary>
    /// 获取当前节点的相邻节点
    /// </summary>
    /// <param name="m">当前节点</param>
    /// <returns></returns>
    public Dictionary<string, MapInfo> AdjacentList(MapInfo m)
    {
        Dictionary<string, MapInfo> resultDic=new Dictionary<string,MapInfo>();

        string left = (m.x - 1) + "-" + m.y;
        string right = (m.x + 1) + "-" + m.y;
        string top = m.x + "-" + (m.y - 1);
        string bot = m.x + "-" + (m.y + 1);

        if (map.ContainsKey(left))
        {
            if(map[left].tag==0)
                resultDic.Add(left, map[left]);
        }

        if (map.ContainsKey(right))
        {
            if (map[right].tag == 0)
                resultDic.Add(right, map[right]);
        }

        if (map.ContainsKey(top))
        {
            if (map[top].tag == 0)
                resultDic.Add(top, map[top]);
        }

        if (map.ContainsKey(bot))
        {
            if (map[bot].tag == 0)
                resultDic.Add(bot, map[bot]);
        }
        return resultDic;
    }

    /// <summary>
    /// 获得两个点的曼哈顿距离
    /// 作为估值函数
    /// </summary>
    /// <param name="st"></param>
    /// <param name="end"></param>
    /// <returns></returns>
    public int GetManhattanDistance(MapInfo st, MapInfo end)
    {
        int result = 0;
        result = Mathf.Abs(st.x - end.x) + Mathf.Abs(st.y - end.y);
        return result;
    }

    /// <summary>
    /// 输出路径
    /// </summary>
    /// <param name="end">终点</param>
    public void PrintThePath(MapInfo end)
    {
        string s = "";
        MapInfo m = end;
        while (m.parent != null)
        {
            s += "("+m.parent.x + "," + m.parent.y + ")->";            
            m = m.parent;
        }
        Debug.Log(s);
    }
}


标签: A Star A*

new 发布于 2016-3-1 01:37

斗牛算法C# 各种技巧

斗牛算法

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Reflection;

namespace ConsoleApplication1
{
    public enum Suits
    {
        Spade = 4,
        Heart = 3,
        Diamond = 2,
        Club = 1,
    }

    public struct CardChip
    {
        public Suits suit;
        public int point;
        public string name;
        public byte suitName;
    }

    /// <summary>
    /// 结果类型
    /// </summary>
    public struct CardsResult
    {
        public ResultType type;
        public int resultPoint;
        public CardChip theMax;
    }

    public enum ResultType
    {
        NoCow = 0,
        CowOne,
        CowTwo,
        CowThree,
        CowFour,
        CowFive,
        CowSix,
        CowSeven,
        CowEight,
        CowNine,
        CowTen,
        SilverCow,
        GoldCow,
        FiveSmall,
        Boom
    }

    public class Player
    {
        public int playerID;
        public List<CardChip> cardList = new List<CardChip>();
        public CardsResult Result
        {
            get { return this.CalcResult(); }
        }

        /// <summary>
        /// show1
        /// </summary>
        public void ShowCards()
        {
            Console.WriteLine("Player:" + playerID);
            foreach (CardChip cp in cardList)
            {
                string a = cp.name + "";
                string b = "";
                if (cp.suit == Suits.Heart)
                    b = (char)3 + "";
                else if (cp.suit == Suits.Diamond)
                    b = (char)4 + "";
                else if (cp.suit == Suits.Club)
                    b = (char)5 + "";
                else
                    b = (char)6 + "";

                Console.Write(b + a + ",");
            }
            Console.WriteLine();
        }

        /// <summary>
        /// show2
        /// </summary>
        public void ShowCrads2()
        {
            Console.WriteLine("Player:" + playerID);
            foreach (CardChip cp in cardList)
            {
                string a = cp.name + "";
                string b = "";
                if (cp.suit == Suits.Heart)
                    b = (char)3 + "";
                else if (cp.suit == Suits.Diamond)
                    b = (char)4 + "";
                else if (cp.suit == Suits.Club)
                    b = (char)5 + "";
                else
                    b = (char)6 + "";

                Console.WriteLine("┌───┐");
                Console.WriteLine("│" + b + "     │");
                Console.WriteLine("│  " + a.PadRight(4) + "│");
                Console.WriteLine("│     " + b + "│");
                Console.WriteLine("└───┘");
            }
            Console.WriteLine();
        }

        /// <summary>
        /// 排序
        /// </summary>
        public void Sort()
        {
            cardList.Sort(
                delegate(CardChip cc1, CardChip cc2)
                {
                    if (cc1.point == cc2.point)
                    {
                        return cc1.suit.CompareTo(cc2.suit);
                    }
                    return cc1.point.CompareTo(cc2.point);
                });
        }

        /// <summary>
        /// 计算牌点数
        /// </summary>
        /// <returns></returns>
        private CardsResult CalcResult()
        {
            CardsResult result;
            result.type = ResultType.NoCow;
            result.resultPoint = 0;
            result.theMax = new CardChip();

            if (Boom(cardList))
            {
                result.theMax = cardList[cardList.Count - 1];
                result.resultPoint = (int)ResultType.Boom;
                result.type = ResultType.Boom;
                return result;
            }

            if (FiveSmall(cardList))
            {
                result.theMax = cardList[cardList.Count - 1];
                result.resultPoint = (int)ResultType.FiveSmall;
                result.type = ResultType.FiveSmall;
                return result;
            }

            List<CardChip> colorCards = new List<CardChip>();
            List<CardChip> noColorCards = new List<CardChip>();

            for (int i = 0; i < cardList.Count; i++)
            {
                if (cardList[i].point >= 10)
                {
                    colorCards.Add(cardList[i]);
                }
                else
                {
                    noColorCards.Add(cardList[i]);
                }
            }

            switch (colorCards.Count)
            {
                case 0:
                    return NoColorCard(cardList);
                case 1:
                    return OneColorCard(cardList);
                case 2:
                    return TwoColorCard(cardList);
                case 3:
                case 4:
                case 5:
                    return MoreThanThreeColorCard(cardList);
            }
            return result;
        }

        /// <summary>
        /// 炸弹
        /// </summary>
        /// <param name="list"></param>
        /// <returns></returns>
        private bool Boom(List<CardChip> list)
        {
            //(b|c|d)==a
            if ((list[1].point | list[2].point | list[3].point) == list[0].point)
            {
                return true;
            }

            return false;
        }

        /// <summary>
        /// 五小
        /// </summary>
        /// <param name="list"></param>
        /// <returns></returns>
        private bool FiveSmall(List<CardChip> list)
        {
            int res = list[0].point + list[1].point + list[2].point + list[3].point + list[4].point;
            if (res <= 10)
            {
                return true;
            }
            return false;
        }

        /// <summary>
        /// 三四五花
        /// </summary>
        /// <param name="list"></param>
        /// <returns></returns>
        private CardsResult MoreThanThreeColorCard(List<CardChip> list)
        {
            CardsResult cdResult;
            cdResult.theMax = list[list.Count - 1];
            int res = (list[0].point + list[1].point) % 10;
            if (res == 0)
            {
                cdResult.type = ResultType.GoldCow;
                cdResult.resultPoint = 10;
            }
            else
            {
                cdResult.resultPoint = res;
                cdResult.type = (ResultType)res;
            }

            return cdResult;
        }

        /// <summary>
        /// 二花
        /// </summary>
        /// <param name="list"></param>
        /// <returns></returns>
        private CardsResult TwoColorCard(List<CardChip> list)
        {
            CardsResult cdResult;
            cdResult.theMax = list[list.Count - 1];

            if ((list[0].point + list[1].point) % 10 == 0)
            {
                cdResult.resultPoint = list[2].point;
                cdResult.type = (ResultType)list[2].point;
            }
            else if ((list[0].point + list[2].point) % 10 == 0)
            {
                cdResult.resultPoint = list[1].point;
                cdResult.type = (ResultType)list[1].point;
            }
            else if ((list[1].point + list[2].point) % 10 == 0)
            {
                cdResult.resultPoint = list[0].point;
                cdResult.type = (ResultType)list[0].point;
            }
            else if ((list[0].point + list[1].point + list[2].point) % 10 == 0)
            {
                cdResult.resultPoint = 10;
                cdResult.type = ResultType.CowTen;
            }
            else
            {
                cdResult.resultPoint = 0;
                cdResult.type  = ResultType.NoCow;
            }

            return cdResult;
        }

        /// <summary>
        /// 一花
        /// </summary>
        /// <param name="list"></param>
        /// <returns></returns>
        private CardsResult OneColorCard(List<CardChip> list)
        {
            CardsResult cdResult;
            int temp = 0;
            if ((list[0].point + list[1].point) % 10 == 0)
            {
                temp = (list[2].point + list[3].point) % 10;
                if (temp == 0)
                {
                    cdResult.resultPoint = 10;
                    cdResult.type = ResultType.CowTen;
                }
                else
                {
                    cdResult.resultPoint = temp;
                    cdResult.type = (ResultType)temp;
                }
            }
            else if ((list[0].point + list[2].point) % 10 == 0)
            {
                temp = (list[1].point + list[3].point) % 10;
                if (temp == 0)
                {
                    cdResult.resultPoint = 10;
                    cdResult.type = ResultType.CowTen;
                }
                else
                {
                    cdResult.resultPoint = temp;
                    cdResult.type = (ResultType)temp;
                }
            }
            else if ((list[0].point + list[3].point) % 10 == 0)
            {
                temp = (list[1].point + list[2].point) % 10;
                if (temp == 0)
                {
                    cdResult.resultPoint = 10;
                    cdResult.type = ResultType.CowTen;
                }
                else
                {
                    cdResult.resultPoint = temp;
                    cdResult.type = (ResultType)temp;
                }
            }
            else if ((list[1].point + list[2].point) % 10 == 0)
            {
                temp = (list[0].point + list[3].point) % 10;
                if (temp == 0)
                {
                    cdResult.resultPoint = 10;
                    cdResult.type = ResultType.CowTen;
                }
                else
                {
                    cdResult.resultPoint = temp;
                    cdResult.type = (ResultType)temp;
                }
            }
            else if ((list[1].point + list[3].point) % 10 == 0)
            {
                temp = (list[0].point + list[2].point) % 10;
                if (temp == 0)
                {
                    cdResult.resultPoint = 10;
                    cdResult.type = ResultType.CowTen;
                }
                else
                {
                    cdResult.resultPoint = temp;
                    cdResult.type = (ResultType)temp;
                }
            }
            else if ((list[2].point + list[3].point) % 10 == 0)
            {
                temp = (list[0].point + list[1].point) % 10;
                if (temp == 0)
                {
                    cdResult.resultPoint = 10;
                    cdResult.type = ResultType.CowTen;
                }
                else
                {
                    cdResult.resultPoint = temp;
                    cdResult.type = (ResultType)temp;
                }
            }
            else if ((list[0].point + list[1].point + list[2].point) % 10 == 0)
            {
                cdResult.resultPoint = list[3].point;
                cdResult.type = (ResultType)list[3].point;
            }
            else if ((list[0].point + list[1].point + list[3].point) % 10 == 0)
            {
                cdResult.resultPoint = list[2].point;
                cdResult.type = (ResultType)list[2].point;
            }
            else if ((list[0].point + list[2].point + list[3].point) % 10 == 0)
            {
                cdResult.resultPoint = list[1].point;
                cdResult.type = (ResultType)list[1].point;
            }
            else if ((list[1].point + list[2].point + list[3].point) % 10 == 0)
            {
                cdResult.resultPoint = list[0].point;
                cdResult.type = (ResultType)list[0].point;
            }
            else
            {
                cdResult.resultPoint = 0;
                cdResult.type = ResultType.NoCow;
            }
            cdResult.theMax = list[list.Count - 1];
            return cdResult;
        }

        /// <summary>
        /// 无花
        /// </summary>
        /// <param name="list"></param>
        /// <returns></returns>
        private CardsResult NoColorCard(List<CardChip> list)
        {
            CardsResult cdResult;
            cdResult.theMax = list[list.Count - 1];

            if ((list[0].point + list[1].point + list[2].point) % 10 == 0 && (list[3].point + list[4].point) % 10 == 0)
            {
                cdResult.resultPoint = 10;
                cdResult.type = ResultType.CowTen;
                return cdResult;
            }
            else if ((list[0].point + list[1].point + list[2].point) % 10 == 0 && (list[3].point + list[4].point) % 10 != 0)
            {
                cdResult.resultPoint = (list[3].point + list[4].point) % 10;
                cdResult.type = (ResultType)((list[3].point + list[4].point) % 10);
                return cdResult;
            }

            if ((list[0].point + list[1].point + list[3].point) % 10 == 0 && (list[2].point + list[4].point) % 10 == 0)
            {
                cdResult.resultPoint = 10;
                cdResult.type = ResultType.CowTen;
                return cdResult;
            }
            else if ((list[0].point + list[1].point + list[3].point) % 10 == 0 && (list[2].point + list[4].point) % 10 != 0)
            {
                cdResult.resultPoint = (list[2].point + list[4].point) % 10;
                cdResult.type = (ResultType)((list[2].point + list[4].point) % 10);
                return cdResult;
            }

            if ((list[0].point + list[1].point + list[4].point) % 10 == 0 && (list[2].point + list[3].point) % 10 == 0)
            {
                cdResult.resultPoint = 10;
                cdResult.type = ResultType.CowTen;
                return cdResult;
            }
            else if ((list[0].point + list[1].point + list[4].point) % 10 == 0 && (list[2].point + list[3].point) % 10 != 0)
            {
                cdResult.resultPoint = (list[2].point + list[3].point) % 10;
                cdResult.type = (ResultType)((list[2].point + list[3].point) % 10);
                return cdResult;
            }

            if ((list[0].point + list[2].point + list[3].point) % 10 == 0 && (list[1].point + list[4].point) % 10 == 0)
            {
                cdResult.resultPoint = 10;
                cdResult.type = ResultType.CowTen;
                return cdResult;
            }
            else if ((list[0].point + list[2].point + list[3].point) % 10 == 0 && (list[1].point + list[4].point) % 10 != 0)
            {
                cdResult.resultPoint = (list[1].point + list[4].point) % 10;
                cdResult.type = (ResultType)((list[1].point + list[4].point) % 10);
                return cdResult;
            }

            if ((list[0].point + list[2].point + list[4].point) % 10 == 0 && (list[1].point + list[3].point) % 10 == 0)
            {
                cdResult.resultPoint = 10;
                cdResult.type = ResultType.CowTen;
                return cdResult;
            }
            else if ((list[0].point + list[2].point + list[4].point) % 10 == 0 && (list[1].point + list[3].point) % 10 != 0)
            {
                cdResult.resultPoint = (list[1].point + list[3].point) % 10;
                cdResult.type = (ResultType)((list[1].point + list[3].point) % 10);
                return cdResult;
            }

            if ((list[1].point + list[2].point + list[3].point) % 10 == 0 && (list[0].point + list[4].point) % 10 == 0)
            {
                cdResult.resultPoint = 10;
                cdResult.type = ResultType.CowTen;
                return cdResult;
            }
            else if ((list[1].point + list[2].point + list[3].point) % 10 == 0 && (list[0].point + list[4].point) % 10 != 0)
            {
                cdResult.resultPoint = (list[0].point + list[4].point) % 10;
                cdResult.type = (ResultType)((list[0].point + list[4].point) % 10);
                return cdResult;
            }

            if ((list[1].point + list[2].point + list[4].point) % 10 == 0 && (list[0].point + list[3].point) % 10 == 0)
            {
                cdResult.resultPoint = 10;
                cdResult.type = cdResult.type = ResultType.CowTen;
                return cdResult;
            }
            else if ((list[1].point + list[2].point + list[4].point) % 10 == 0 && (list[0].point + list[3].point) % 10 != 0)
            {
                cdResult.resultPoint = (list[0].point + list[3].point) % 10;
                cdResult.type = (ResultType)((list[0].point + list[3].point) % 10);
                return cdResult;
            }

            if ((list[2].point + list[3].point + list[4].point) % 10 == 0 && (list[0].point + list[1].point) % 10 == 0)
            {
                cdResult.resultPoint = 10;
                cdResult.type = ResultType.CowTen;
                return cdResult;
            }
            else if ((list[2].point + list[3].point + list[4].point) % 10 == 0 && (list[0].point + list[1].point) % 10 != 0)
            {
                cdResult.resultPoint = (list[0].point + list[1].point) % 10;
                cdResult.type = (ResultType)((list[0].point + list[1].point) % 10);
                return cdResult;
            }

            cdResult.resultPoint = 0;
            cdResult.type = ResultType.NoCow;
            return cdResult;
        }

    }

    public class Card
    {
        /// <summary>
        /// The maximum player count
        /// </summary>
        public const int MAX_PLAYERS = 10;

        /// <summary>
        /// 构造
        /// </summary>
        public Card()
        {

        }

        public void Start()
        {
            //Initialize crads
            List<CardChip> cards = this.InitCards();
            //Random crads
            this.RandomCards(cards);
            //Deal cards to players
            Player[] players = Deal(cards, 5, 5);
            //print to screen
            for (int i = 0; i < players.Length; i++)
            {
                players[i].ShowCards();
            }
            //calculate the result for each player
            Console.WriteLine("-----------------------------------------------------");
            for (int k = 0; k < players.Length; k++)
            {
                CardsResult cr = players[k].Result;
                string str = string.Format("Player{0}:牌型-{1} 点数-{2} 最大牌-{3}{4}", k, (ResultType)cr.type, cr.resultPoint, (char)cr.theMax.suitName, cr.theMax.name);
                Console.WriteLine(str);
            }

            CalcWinner(players);
        }

        /// <summary>
        /// 初始化牌13*4  游戏蛮牛http://www.unitymanual.com/space-uid-13769.html  CSDN博客http://write.blog.csdn.net/postlist
        /// </summary>  
        /// <returns></returns>
        public List<CardChip> InitCards()
        {
            List<CardChip> cards = new List<CardChip>();

            for (int i = 1; i <= 13; i++)
            {
                for (int j = 1; j <= 4; j++)
                {
                    CardChip cc;
                    cc.point = i;
                    cc.suit = (Suits)j;
                    if (j == 1) cc.suitName = 4;
                    else if (j == 2) cc.suitName = 5;
                    else if (j == 3) cc.suitName = 3;
                    else cc.suitName = 6;

                    if (i >= 2 && i <= 10)
                        cc.name = i.ToString();
                    else if (i == 1)
                        cc.name = "A";
                    else if (i == 11)
                        cc.name = "J";
                    else if (i == 12)
                        cc.name = "Q";
                    else
                        cc.name = "K";
                    cards.Add(cc);
                }
            }
            return cards;
        }

        /// <summary>
        /// 洗牌
        /// </summary>
        /// <param name="cds"></param>
        public void RandomCards(List<CardChip> cds)
        {
            Permute(cds);
        }

        /// <summary>
        /// Deal crads
        /// </summary>
        /// <param name="cds">洗好的牌</param>
        /// <param name="players">玩家数</param>
        /// <param name="num">每个玩家的牌数</param>
        /// <returns></returns>
        public Player[] Deal(List<CardChip> cds, int players, int num)
        {
            if (players > MAX_PLAYERS)
            {
                Console.WriteLine("Too much players");
                return null;
            }
            Console.WriteLine("----------------------Deal cards----------------------");
            Player[] playerList = new Player[players];
            for (int i = 0; i < playerList.Length; i++)
            {
                playerList[i] = new Player();
                playerList[i].playerID = i;
                playerList[i].cardList = new List<CardChip>();
            }
            for (int j = 0; j < players * num; j++)
            {
                playerList[j % players].cardList.Add(cds[j]);
            }
            for (int k = 0; k < playerList.Length; k++)
            {
                playerList[k].Sort();
            }
            return playerList;
        }

        /// <summary>
        /// Calculate the winner
        /// </summary>
        /// <param name="players"></param>
        public void CalcWinner(Player[] players)
        {
            List<Player> p = players.ToList<Player>();
            p.Sort(
                delegate(Player p1, Player p2)
                {
                    if (p1.Result.type == p2.Result.type)
                    {
                        if (p1.Result.theMax.point == p2.Result.theMax.point)
                        {
                            return p1.Result.theMax.suit.CompareTo(p2.Result.theMax.suit);
                        }
                        return p1.Result.theMax.point.CompareTo(p2.Result.theMax.point);
                    }
                    return p1.Result.type.CompareTo(p2.Result.type);

                });
            Console.WriteLine("----------------------结果---------------------------");
            for (int k = p.Count - 1; k >= 0; k--)
            {
                CardsResult cr = p[k].Result;
                string str = string.Format("Player{0}:牌型-{1} 点数-{2} 最大牌-{3}{4}", p[k].playerID, (ResultType)cr.type, cr.resultPoint, (char)cr.theMax.suitName, cr.theMax.name);
                Console.WriteLine(str);
            }
            Console.WriteLine("-----------------------------------------------------");
            Console.WriteLine(string.Format("玩家{0}获胜!", p[4].playerID));

        }

        #region Random Cards in Array
        private void Permute<T>(List<T> array)
        {
            Random random = new Random();
            for (int i = 1; i < array.Count; i++)
            {
                Swap<T>(array, i, random.Next(0, i));
            }
        }

        private void Swap<T>(List<T> array, int indexA, int indexB)
        {
            T temp = array[indexA];
            array[indexA] = array[indexB];
            array[indexB] = temp;
        }
        #endregion
    }
}

标签: 斗牛算法

new 发布于 2016-3-1 01:35

洗牌算法 各种技巧

洗牌算法
private void Permute<T>(List<T> array)
        {
            Random random = new Random();
            for (int i = 1; i < array.Count; i++)
            {
                Swap<T>(array, i, random.Next(0, i));
            }
        }

        private void Swap<T>(List<T> array, int indexA, int indexB)
        {
            T temp = array[indexA];
            array[indexA] = array[indexB];
            array[indexB] = temp;
        }

标签: 洗牌

new 发布于 2016-3-1 01:33

制作UGUI美术字体 Unity游戏研究

制作美术字体的教程网上有很多了,我借鉴了网上众多大神的方法, 在此感谢他们。

额外工具:BMFont  下载
先用BMFont编辑美术字,并导出文本信息和图片。

PS:导出图片的大小适合你的美术图片集就好,不要有太大浪费。

导出的文件

有了这两个文件就可以在unity里做美术字体了。

先把这两个文件导入unity工程,然后再创建一个customFont和一个材质球。

然后就是读取数据文件了,这里使用了NGUI里的脚本BMFontReader等

再用脚本读取数据并赋到customFont里,代码

using UnityEngine;
using System.Collections;
using UnityEditor;

public class MyFont : Editor
{
    [MenuItem("MakeFont/Make")]
    static void Make()
    {
        Object[] objs = Selection.objects;
        if (objs.Length != 2)
        {
            Debug.LogError("请选中Custom Font文件与BMFont导出的fnt数据文件");
            return;
        }
        Font m_myFont;
        TextAsset m_data;
        if (objs[0].GetType() == typeof(TextAsset)&&objs[1].GetType()==typeof(Font))
        {
            Debug.Log("text");
            m_data = (TextAsset)objs[0];
            m_myFont = (Font)objs[1];
            Debug.Log("FontName:" + m_myFont.name + "\nData:" + m_data.name);
        }
        else if (objs[1].GetType() == typeof(TextAsset) && objs[0].GetType() == typeof(Font))
        {            
            m_data = (TextAsset)objs[1];
            m_myFont = (Font)objs[0];
            Debug.Log("FontName:"+m_myFont.name+"\nData:"+m_data.name);
        }
        else
        {
            Debug.LogError("请选中Custom Font文件与BMFont导出的fnt数据文件");
            Debug.Log("FontName:null" + "\nData:null");
            return;            
        }

        BMFont mbFont = new BMFont();
        BMFontReader.Load(mbFont, m_data.name, m_data.bytes);  // 借用NGUI封装的读取类
        CharacterInfo[] characterInfo = new CharacterInfo[mbFont.glyphs.Count];
        for (int i = 0; i < mbFont.glyphs.Count; i++)
        {
            BMGlyph bmInfo = mbFont.glyphs[i];
            CharacterInfo info = new CharacterInfo();
            info.index = bmInfo.index;
            info.uv.x = (float)bmInfo.x / (float)mbFont.texWidth;
            info.uv.y =1- (float)bmInfo.y / (float)mbFont.texHeight;
            info.uv.width = (float)bmInfo.width / (float)mbFont.texWidth;
            info.uv.height =- (float)bmInfo.height / (float)mbFont.texHeight;
            info.vert.x = (float)bmInfo.offsetX;
            info.vert.y = (float)bmInfo.offsetY;           
            info.vert.width = (float)bmInfo.width;
            info.vert.height = (float)bmInfo.height;
            info.width = (float)bmInfo.advance;
            characterInfo[i] = info;
        }
        m_myFont.characterInfo = characterInfo;

        Debug.Log("OK");
    }
}

操作方法:选中customFont文件和导出的数据文件,再点击菜单 MakeFont>>Make,这样就把数据绑定了。

接下来就是把图片丢到材质球上,再把材质球丢到customFont的Default Material里(也可以不丢)。

然后创建一个Text看下效果,

PS:如果字体重叠了,可以把Text的width加大。下面是图片和材质等的设置,可参考。

这个shader是拿的国外一个收费插件的,花了我13刀!可以向我要。

字体文件包括customFont,材质,图片。


new 发布于 2016-3-1 01:28

你get了无数技能,为什么一事无成 人生杂谈

前几日看到阮一峰老师的发的一句话,颇有感慨,「你只是坐在电脑前,往网上发表了一段文字或者一张图片,随便什么,就能够接触到多少陌生的灵魂。这就是我热爱互联网的原因」。我打心底认为这是一个最好的时代,这个时代,我们能接触的信息比历史上任何时候都多,我们通过互联网能够轻易的分享自己的喜悦,传播自己的思想,正如我此刻正在敲的这些文字。
 
今天并不是想吹嘘信息时代有多好,毕竟我们都还生活在墙里头呢。今天只是谈谈我的一些思考,处于信息大潮下的我们,该以怎样的视角来审视这个时代,在信息时代的物竞天择中,我们如何能爬向食物链的顶端。
 
牛逼吹大了,好像我要分分钟教你做人的架势。其实我想说的是一项很容易被大家忽略的技能:信息获取。可能有些人不认为这是一项需要练习的技能,还有些人可能已经习惯了自己的阅读方式,对此不以为然。
 
其实这是一项尤为重要的基础技能,尤其是在信息爆炸的今天。这就好比是一个人吃饭的方式,有的人吃饭的时候脑子放空一切,盯着肉眼珠都不转一下,用生命在享受这顿饭,他一定会成功的吃胖。相反,有的人吃饭的时候脑子里还在想那个bug该怎么解,今天下午还有多少事情要做,吃进肚子的是啥都忘了。他不专注吃,不认真吃,在吃这件事上完全没有竞争力,所以他怎么吃都不胖。
 
信息的获取和脂肪的获取,道理是一样的,姿势正确,你才能吸收到精华。处在信息时代的我们,如何才能利用好身边的资源,实现理想,迎娶白富美,走上人生颠覆呢?我们不妨回顾一下历史,看看能得到什么启示。
 
倘若现在是农耕时代,你通过什么途径能从一介平民走向成功呢?农耕时代的核心资源就是土地,你唯有辛勤劳作,面朝黄土背朝天,跟牲口似的使唤自己,然后才能余下一点钱。再置办一些土地,增加粮食产量,把余下的地租给佃户来收租,慢慢从贫农、中农、富农走向小地主,这就是你的发展之路。事实上我老家的大军阀阎锡山家族就是这样的发展历程,全靠祖辈玩命似的折腾,才能在他这辈的时候成为小地主阶级,过上相对殷实的生活。
 
如果是工业时代呢?生产力技术是核心资源,开办工厂,提高生产效率,最终走向企业家的成功之路。
 
现在是信息时代了,核心资源是什么呢?那就是信息。更具体点,是你每天浏览的网站,是你每个半小时就刷一次的微博,是知乎,是豆瓣,是朋友圈。天呐!这个时代的核心资源每天都在你眼前流过!你不兴奋吗?
 
我不兴奋。因为太多了。
 
这是多么实诚的一句话。这是信息时代,也是信息过剩的时代。每个领域都有N多竞争产品,还有更多的营销高手在挖空心思挖掘人性的种种缺点,只为让你多看他们一眼。
 
老子根本看不过来啊!所以,碎片化阅读成了我们的习惯,甚至成为了一种行为模式。你花2分钟的时间能刷100条微博,然后高速运转的大脑从中挑选出一两条有价值的,花2秒钟时间完成转发,顶多再加一句「新技能get」。然后熟练地关闭微博打开朋友圈继续刷,无缝切换。而你刚刚get的《excel的100种使用技巧》或是《每天10分钟的神奇减肥操》早已抛之脑后。
 
更有快者,只看了文章的标题就算是get了,内容都可以不看。你跟他一聊,感觉这人什么都知道,深入探讨,却无法再言。难怪现在标题党盛行。
 
用这样的方式获取信息,会造成我们只知结论而不知其所以然,我们没有真正去思考和探索,而只是简单的被动接受观点。这样的危害是巨大的,你甚至都无法形成自己的观点,没有自己的思想。又如何能在工作中打造自己的理念,发挥自己的创造力呢?
 
我很早就对碎片化阅读持有警惕,看似高效率的阅读,实际上能真正吸收的信息少之又少,占比连5%都达不到。所以你感觉上get了无数技能,实际上却一无所获。你还是不会在excel中调格式,你还是一个胖子。
 
你花同样的时间,静下心来,慢慢地阅读一篇文章,或是读一本书中的某个章节,这样你能真正吸收的内容就相当多。你精细阅读并且伴随思考,这样获取的信息才能真正融入到你的思维中,而不是只在大脑中走个过场。所以我现在看文章的时候会刻意提示自己,慢一点,再慢一点。我记得我在读《失控》这本书的时候,甚至每读一段都要停下来思考一下,真正理解了书中内容后才会继续往下读。
 
看似又笨又慢的阅读方式,总体算下来要比碎片化阅读所获取的信息多很多。所以,在此建议各位朋友,不妨静下来,慢下来去阅读。不如,就从这篇文章开始吧~
 
能够“真正阅读”信息之后,还有一项能力十分重要,那就是对信息的真伪判断。毕竟我们每天接收的信息太多了 。有些信息我们不去辨别它的真伪就一股脑全部吸收,甚至还会传播给其他人,最终形成人云亦云的局面,真相都被蒙蔽了。
 
我并不是想强调我们要掌握真相,而是要强调对于不确切的信息,我们要有「求证」的过程。比如:发改委发布红头文件勒令房价降一半。你至少去发改委的网站查一下有没有这个信息,有时候只是很简单的一步,只是我们缺乏这个意识。明智与无知有时候只差一步。
 
再有就是,对于自己没有求证过的信息,不要轻易的传播给其他人。如果你实在憋不住,至少在前面加两个字:据说。比如「360是流氓,盗取用户信息」,你有做过实验吗?你有确切的证据能说明问题吗?我相信对于这条信息很多人都是“听别人说”,不要以为我只是随便跟人讲讲没什么大不了的,且不说对别人的影响,于你自己而言,就已经决定了你的思维,是在理智在一边,还是在蒙昧这一边。
 
所以,对待信息,我们要进行必要的求证,只有这样才能掌握一手信息,离真相更近一步。
 
在真正吸收信息,能甄别信息的真伪之后,我们还有一个技能需要学习,那就是判断信息的质量。毕竟每天你过目的信息太多了,我们要留下的是那些真正有用的,能对你的思维或是工作产生影响的信息。
 
像马云说什么什么,马化腾说什么什么之类的,就不要过于热捧了。他们说的是对的,但是离你太远了,你还没有到了领航一个大企业的阶段。你每天微博中的那些搞笑排行榜、各种段子手,营销帐号,每天废话的人,把他们取关吧,我自己也刚刚做完这件事。
 
你看了无数笑话,但你并不开心。
 
什么样的信息对你是有价值的呢?我相信不同人有不同的标准,所以这里就不评判了。我想说的是,不管你的标准是什么,你一定要有这个意识,那就是一定要去鉴别这个信息,否则你还是一个好坏兼收的大脑,说白了,你还是没有形成自己的思维和立场。
 
这是一个伟大的时代,这个时代最值钱的核心资源,它就在你我左右。光是利用信息不对称,就能产生巨大的商机,占领信息高地者,就能指挥信息落后者的行为。互联网是如此美妙,不要光用互联网找乐子打游戏了,去挖掘这个时代的秘密花园吧。
 

那么,到结束的时候了,该反思一下自己了,这篇文章你好好看了吗?是不是只看了标题就走了?是不是真正吸收了文章的思想?还是只是点了赞?


来源:http://www.cnblogs.com/lvdabao/p/5212536.html


new 发布于 2016-3-1 01:19

uGUI长按事件 Unity游戏研究

突然发现uGUI没有给出可以直接用的长按事件。。。

上个没有注释的代码,代码说明一切。

using UnityEngine;
using System.Collections;
using UnityEngine.Events;
using UnityEngine.EventSystems;

public class UILongPressEvent : MonoBehaviour,IPointerDownHandler,IPointerExitHandler,IPointerUpHandler
{
    [SerializeField]
    UnityEvent m_onLongPress = new UnityEvent();

    float interval = 0.1f;
    float longPressDelay = 0.5f;

    private bool isTouchDown = false;
    private bool isLongpress = false;
    private float touchBegin = 0;
    private float lastInvokeTime = 0;

    // Update is called once per frame
    void Update () 
    {
        if (isTouchDown)
        {
            if (isLongpress)
            {
                if (Time.time - lastInvokeTime > interval)
                {
                    m_onLongPress.Invoke();
                    lastInvokeTime = Time.time;
                }
            }
            else
            {
                if (Time.time - touchBegin > longPressDelay)
                {
                    isLongpress = true;
                }
            }
        }
    }

    public void OnPointerDown(PointerEventData eventData)
    {
        touchBegin = Time.time;
        isTouchDown = true;
    }

    public void OnPointerExit(PointerEventData eventData)
    {
        isTouchDown = false;
        isLongpress = false;
    }

    public void OnPointerUp(PointerEventData eventData)
    {
        isTouchDown = false;
        isLongpress = false;
    }
}



标签: uGUI 长按

new 发布于 2016-2-25 09:40