<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    where the amazing happens

    算法2 : 動態規劃

    動態規劃最優化原理中的一種重要的方法。

    動態規劃在查找有很多重疊子問題的情況的最優解時有效。它將問題重新組合成子問題。為了避免多次解決這些子問題,它們的結果都逐漸被計算并被保存,從簡單的問題直到整個問題都被解決。因此,動態規劃保存遞歸時的結果,因而不會在解決同樣的問題時花費時間。

    動態規劃只能應用于有最優子結構的問題。最優子結構的意思是局部最優解能決定全局最優解。簡單地說,問題能夠分解成子問題來解決。

    總的來說,動態規劃的優勢在于:

    • 重疊子問題
    • 最優子結構
    • 記憶化


    問題描述:
    動態規劃舉例
    圖10-3(a)示出了一個數字三角形,請編一個程序,
    計算從頂至底的某處的一條路勁,
    使該路勁所經過的數字的總和最大。
    (1) 每一步可沿左斜線向下或右斜線向下;
    (2) 1<三角形行數≤100;
    (3) 三角形中的數字為0,1,……99。
    輸入數據:
    由INPUT.TXT文件中首先讀到的是三角形的行數,
    在例子中INPUT.TXT表示如圖13-3(b).?
    ???????????????????????????????
    ?????????????????????????????? 7?
    ????????????????????????????? 3 8?
    ???????????????????????????? 8 1 0?
    ????????????????????????????2 7 4 4?
    ???????????????????????????4 5 2 6 5
    ????????????????????????? 5 6 9 5 9 8



    從別人blog里看到這個題目,手上癢癢,就寫了一個.用的是逆向遞推法從頂部往下.
    分2個文件,一個主程序和一個用于讀取文件的輔助類.


    思路:
    ? 1.算出每個節點的規劃值(也就是待比較的最大值),并記錄搜索路徑
    ??2.取三角形底邊所有規劃值中的最大值
    ? 3.輸出路徑

    主程序

    package ?test;
    import ?java.util. * ;

    /**
    ?*??用動態規劃法求出最優路徑
    ?*??
    @author ?zqc
    ?*?
    */

    public ? class ?DynamicSolveTrianglePath? {
    ????
    ????
    private ?String[][]?str_triangle? = ? null ;
    ????
    private ?Node[][]?triangle_nodes? = ? null ;
    ????
    private ?List?nodes;
    ????
    private ?List?paths;
    ????
    ????
    // 節點
    ???? static ? class ?Node {
    ????????
    private ? int ?value;
    ????????
    private ?List?path? = ? new ?Vector();
    ????????
    public ?List?getPath()? {
    ????????????
    return ?path;
    ????????}

    ????????
    public ? void ?setPath(List?p) {
    ????????????path?
    = ?p;
    ????????}

    ????????
    // n=(0,0)?or?(0,1)?or?(2,2)
    ???????? public ? void ?addPath(String?n) {
    ????????????path.add(n);
    ????????}

    ????????
    public ? void ?addPath(List?pa) {
    ????????????path.addAll(pa);
    ????????}

    ????????
    public ? int ?getValue()? {
    ????????????
    return ?value;
    ????????}

    ????????
    public ? void ?setValue( int ?value)? {
    ????????????
    this .value? = ?value;
    ????????}

    ????}

    ????
    ????
    public ?DynamicSolveTrianglePath() {
    ????????initNodes();
    ????????findPath();
    ????}

    ????
    ????
    //根節點開始,逆向推解出到達所有節點的最佳路徑
    ????private?void?initNodes(){
    ????????
    this.str_triangle?=?ReadTriangle.getTriangle();
    ????????triangle_nodes?
    =?new?Node[str_triangle.length][];
    ????????nodes?
    =?new?Vector();
    ????????
    for(int?i?=?0?;?i?<?str_triangle.length;?i++){
    ????????????triangle_nodes[i]?
    =?new?Node[str_triangle[i].length];
    ????????????
    for(int?j?=?0?;?j<str_triangle[i].length;j++){
    ????????????????String?currentPath?
    =?"("+i+","+j+")";
    ????????????????Node?n?
    =?new?Node();
    ???????????????
    if(i==0&&j==0){
    ???????????????????n.setValue(
    ??????????????????????????????c(str_triangle[
    0][0])????????
    ????????????????????????????);
    ???????????????????n.addPath(currentPath);
    ???????????????????triangle_nodes[i][j]?
    =?n;
    ???????????????????
    continue;
    ???????????????}

    ???????????????
    //左右邊界節點
    ???????????????if((j==0||j==str_triangle[i].length-1)){
    ???????????????????
    if(i==1){//第2行的節點
    ???????????????????????int?value?=?c(str_triangle[0][0])+c(str_triangle[i][j]);
    ???????????????????????List?ph?
    =?triangle_nodes[0][0].getPath();
    ???????????????????????n.addPath(ph);
    ???????????????????????n.addPath(currentPath);
    ???????????????????????n.setValue(value);
    ???????????????????????ph?
    =?null;
    ???????????????????}
    else{//0,1行以下的其他邊界節點
    ?????????????????????int?value?=?j==0?c(str_triangle[i][j])+triangle_nodes[i-1][j].getValue():
    ?????????????????????????c(str_triangle[i][j])
    +triangle_nodes[i-1][j-1].getValue();
    ?????????????????????List?ph?
    =?j==0?triangle_nodes[i-1][j].getPath():
    ?????????????????????????triangle_nodes[i
    -1][j-1].getPath();
    ?????????????????????n.addPath(ph);
    ?????????????????????n.addPath(currentPath);
    ?????????????????????n.setValue(value);
    ???????????????????}

    ???????????????}
    else{//除邊界節點外其他節點
    ???????????????????????Node?node1?=?triangle_nodes[i-1][j-1];
    ???????????????????????Node?node2?
    =?triangle_nodes[i-1][j];
    ???????????????????????Node?bigger?
    =?max(node1,node2);
    ???????????????????????List?ph?
    =?bigger.getPath();
    ???????????????????????n.addPath(ph);
    ???????????????????????n.addPath(currentPath);
    ???????????????????????
    int?val?=?bigger.getValue()+c(str_triangle[i][j]);
    ???????????????????????n.setValue(val);
    ???????????????}

    ??????????????triangle_nodes[i][j]?
    =?n;?
    ??????????????n?
    =?null;
    ????????????}
    //end?of?for?j
    ????????}
    //end?of?for?i
    ????}

    ????
    ????
    private?Node?max(Node?node1,Node?node2){
    ????????
    int?i1?=?node1.getValue();
    ????????
    int?i2?=?node2.getValue();
    ????????
    return?i1>i2?node1:node2;
    ????}

    ????
    ????
    private?int?c(String?s){
    ????????
    return?Integer.parseInt(s);
    ????}

    ????
    ????
    //找出最佳路徑
    ????private?void?findPath(){
    ????????
    if(this.triangle_nodes==null)return;
    ????????
    int?max?=?0;
    ????????
    int?mi?=?0;
    ????????
    int?mj?=?0;
    ????????
    for(int?i?=?0?;?i?<?triangle_nodes.length;?i++){
    ????????????
    for(int?j?=?0?;?j<triangle_nodes[i].length;j++){
    ????????????????
    int?t?=?triangle_nodes[i][j].getValue();
    ????????????????
    if(t>max){
    ????????????????????max?
    =?t;
    ????????????????????mi?
    =?i;
    ????????????????????mj?
    =?j;
    ????????????????}

    ????????????}

    ????????}

    ????????System.out.println(
    "Max?Path:"+triangle_nodes[mi][mj].getPath());
    ????????System.out.println(
    "Max?Value:"+max);
    ????}

    ????
    ????
    public?static?void?main(String[]?args)throws?Exception{
    ????????DynamicSolveTrianglePath?dsp?
    =?new
    ???????????DynamicSolveTrianglePath();
    ????}

    ????
    }

    用于讀取文件的輔助類

    package ?test;
    import ?java.io. * ;
    import ?java.util. * ;

    /**
    ?*??輸入文本格式為
    ?*??類似這樣一個數字三角形
    ?*??
    ?*??????????x
    ?*?????????x?x
    ?*????????x?x?x
    ?*???????x?x?x?x
    ?*??????x?x?x?x?x?
    ?*??????
    ?*??
    @author ?zqc
    ?*?
    */

    public ? class ?ReadTriangle? {

    ????
    public ? static ?String?TRIANGLE_FILE? = ? " d:/triangle.txt " ;
    ????
    ????
    public ? static ?String[][]?getTriangle() {
    ????????String[][]?rtn;
    ????????
    try ? {
    ????????????File?f?
    = ? new
    ???????????????????File(ReadTriangle.TRIANGLE_FILE);
    ????????????BufferedReader?br?
    = ? new ?
    ????????????????BufferedReader(
    ???????????????
    new ?FileReader(f)????????
    ????????????);
    ????????????List?l?
    = ? new ?Vector();
    ????????????String?line?
    = ?br.readLine();
    ????????????
    while (line != null ) {
    ????????????????l.add(line.trim());
    ????????????????line?
    = ?br.readLine();
    ????????????}

    ????????????
    int ?heigth? = ?l.size();
    ????????????rtn?
    = ? new ?String[heigth][];
    ????????????
    for ( int ?i? = ? 0 ?;?i? < ?heigth?;?i ++ ) {
    ????????????????String?s?
    = ?(String)l.get(i);
    ????????????????String[]?tk?
    = ?s.split( " ? " );
    ????????????????
    int ?tklen? = ?tk.length;
    ????????????????rtn[i]?
    = ? new ?String[tklen];
    ????????????????
    for ( int ?k? = ? 0 ?;?k? < ?tklen?;?k ++ ) {
    ????????????????????rtn[i][k]?
    = ?tk[k];
    ????????????????}

    ????????????}

    ????????????
    return ?rtn;
    ????????}
    ? catch ?(FileNotFoundException?e)? {
    ????????????e.printStackTrace();
    ????????}
    ? catch ?(IOException?e)? {
    ????????????e.printStackTrace();
    ????????}

    ????????
    return ? null ;
    ????}

    ????
    }


    結果輸出如下:

    Max Path:[(0,0), (1,0), (2,0), (3,1), (4,1), (5,2)]
    Max Value:39


    同樣的方法可以解決很多類似的問題,比如,游戲中的最短路徑;最優化投資問題;背包問題等等.

    posted on 2006-04-23 20:47 where the amazing happens 閱讀(1813) 評論(5)  編輯  收藏 所屬分類: 算法&數據結構

    評論

    # re: 算法2 : 動態規劃 2006-05-09 08:27 T.Sing

    排列三角形 你居然用節點寫,服了...  回復  更多評論   

    # re: 算法2 : 動態規劃 2006-05-10 15:46 鳥不生蛋蛋的地方

    只要思路清晰,代碼自然而然也就寫出來了,不過肯定不是最好的方法:)  回復  更多評論   

    # re: 算法2 : 動態規劃 2006-05-21 10:49 123

    、用關系“<”和“=”將3個數A、B和C依次排列時,有13種不同的序關系:
    A=B=C,A=B<C,A<B=C,A<B<C,A<C<B,A=C<B,B<A=C,
    B<A<C,B<C<A,B=C<A,C<A=B,C<A<B,C<A<B。
    若要將n個數依序進行排列,試設計一個動態規劃算法,計算出有多少鐘不同的序關系?



    求解,謝謝  回復  更多評論   

    # re: 算法2 : 動態規劃 2006-05-22 16:40 鳥不生蛋蛋的地方

    樓上的兄弟,最近事情比較多沒法靜下來好好想.如果不急的話請留下email地址.  回復  更多評論   

    # re: 算法2 : 動態規劃 2006-07-11 17:45 iris

    可否把那個動態規劃排序的程序發我一份?我看了你5.22的留言,不好意思不知道還在不在?謝謝
    junmei0825@sina.com  回復  更多評論   


    只有注冊用戶登錄后才能發表評論。


    網站導航:
     

    公告

    點擊這里給我發消息

    導航

    <2006年4月>
    2627282930311
    2345678
    9101112131415
    16171819202122
    23242526272829
    30123456

    統計

    常用鏈接

    留言簿(3)

    隨筆分類(18)

    隨筆檔案(17)

    文章分類

    相冊

    其他我的blog

    技術Blog

    最新隨筆

    搜索

    最新評論

    閱讀排行榜

    評論排行榜

    主站蜘蛛池模板: 国产在线观看片a免费观看| 亚洲av中文无码| 亚洲精品亚洲人成在线| 日韩一区二区在线免费观看| 国产福利在线观看永久免费| 午夜亚洲AV日韩AV无码大全| 成人免费男女视频网站慢动作| 午夜肉伦伦影院久久精品免费看国产一区二区三区 | 亚洲AV无码国产精品麻豆天美| 最好看的中文字幕2019免费| 亚洲中文无码mv| 日日噜噜噜噜夜夜爽亚洲精品| 亚洲电影免费观看| 免费夜色污私人影院网站| 亚洲精品白色在线发布| 亚洲无砖砖区免费| 国产资源免费观看| 99爱免费观看视频在线| 边摸边吃奶边做爽免费视频网站 | 日韩插啊免费视频在线观看| 亚洲人成欧美中文字幕| 亚洲av无码一区二区三区不卡 | 91免费资源网站入口| 国产精品偷伦视频免费观看了| 亚洲国产成人精品久久| 国产成人A亚洲精V品无码| 国语成本人片免费av无码| 国产做国产爱免费视频| 亚洲欧美日韩中文高清www777| 亚洲高清国产AV拍精品青青草原| 女人18毛片a级毛片免费| 无码精品一区二区三区免费视频| 国产精品亚洲片在线花蝴蝶| 亚洲第一区视频在线观看| 国产成人精品亚洲精品| 国产在线播放免费| 免费a级毛片无码a∨蜜芽试看| 午夜视频免费在线观看| 国产精品美女久久久免费 | 永久免费无码网站在线观看个| 亚洲国产成人无码av在线播放|