LeetCode071 Simplify Path

详细见:leetcode.com/problems/simplify-path


Java Solution: github

package leetcode;

/*
 * 	Given an absolute path for a file (Unix-style), simplify it.

	For example,
	path = "/home/", => "/home"
	path = "/a/./b/../../c/", => "/c"
	click to show corner cases.
	
	Corner Cases:
	Did you consider the case where path = "/../"?
	In this case, you should return "/".
	Another corner case is the path might contain multiple slashes '/' together, such as "/home//foo/".
	In this case, you should ignore redundant slashes and return "/home/foo".
 */

public class P071_SimplifyPath {
	/*
	 * 	建立最简单的树形结构
	 * 	6 ms
	 */
	static class Solution1 {
	    public String simplifyPath(String path) {
	    	int len = 0;
	    	if (path == null || (len = path.length()) < 2)
	    		return path;
	    	Node head = new Node(), cur = head;
	    	StringBuilder st = new StringBuilder();
	    	boolean isLastSlash = true;
	    	boolean isLastDot = false;
	    	boolean isDoubleDot = false;
	    	boolean isDoubleDotLast = false;
	    	for (int i = 0; i <= len; i ++) {
	    		char c = '\0';
	    		if (i == len || (c = path.charAt(i)) == '/') {
	    			if (isLastSlash || (isLastDot && ! isDoubleDot)) {
	    				if (st.length() != 0)
	    					st = new StringBuilder();
	    				isLastSlash = true;
	    				isDoubleDot = false;
	    				continue;
	    			}
	    			if (isDoubleDot) {
	    				if (st.length() == 2) {
	    					if (i != len) {
	    						cur = cur.pre == null ? cur : cur.pre;
	    						isDoubleDotLast = true;
	    					} else {
	    						if (cur.pre != null)
	    							cur.pre.next = null;
	    					}
	    				} else {
	    					if (! st.toString().equals(".")) {
		    					Node temp = new Node();
		    	    			temp.str = st.toString();
		    	    			temp.pre = cur;
		    	    			cur.next = temp;
		    	    			cur = temp;
	    					}
	    				}
		    			st = new StringBuilder();
		    			isDoubleDot = false;
	    				continue;
	    			}
	    			if (! st.toString().equals(".")) {
		    			Node temp = new Node();
		    			temp.str = st.toString();
		    			temp.pre = cur;
		    			cur.next = temp;
		    			cur = temp;
	    			}
	    			st = new StringBuilder();
	    			isDoubleDot = false;
	    			isLastDot = false;
	    			isLastSlash = true;
	    		} else if (c == '.') {
	    			if (isLastDot)
	    				isDoubleDot = true;
	    			st.append(".");
	    			isLastDot = true;
	    			isLastSlash = false;
	    			isDoubleDotLast = false;
	    		} else {
	    			st.append(c);
	    			isDoubleDot = false;
	    			isLastDot = false;
	    			isLastSlash = false;
	    			isDoubleDotLast = false;
	    		}
	    	}
	    	if (isDoubleDotLast && cur != null)
	    		cur.next = null;
	    	if (cur.str == null)
	    		cur.next = null;
	    	if (cur.next != null)
	    		cur.next = null;
	    	Node travel = head;
	    	StringBuilder ans = new StringBuilder();
	    	while (travel != null) {
	    		ans.append(travel.str == null ? "/" : travel.str);
	    		if (travel != head && travel.next != null)
	    			ans.append("/");
	    		travel = travel.next;
	    	}
			return ans.toString();
	    }
	    static class Node {
	    	String str = null;
	    	Node pre;
	    	Node next;
	    	public Node() {}
	    	public Node(String str, Node pre, Node next) {
	    		this.str = str;
	    		this.pre = pre;
	    		this.next = next;
	    	}
	    }
	}
}


C Solution: github

/*
    url: leetcode.com/problems/simplify-path
    AC 6ms 28.00%
*/

#include <stdio.h>
#include <stdlib.h>

//element type
typedef int T;
typedef struct dll sdll;
typedef struct dll * pdll;
typedef struct dln sdln;
typedef struct dln * pdln;


//doubly list node
struct dln {
    T val;
    pdln pre;
    pdln nxt;
};

//doubly linked list
struct dll {
    pdln first;
    pdln last;
    int size;
};

pdll dll_init() {
    pdll l = (pdll) malloc(sizeof(sdll));
    l->first = NULL;
    l->last = NULL;
    l->size = 0;
    return l;
}

void dll_add_first(pdll l, T v) {
    pdln t = (pdln) malloc(sizeof(sdln));
    t->val = v;
    t->pre = NULL;
    t->nxt = NULL;
    if (l->size == 0) {
        l->first = t;
        l->last = t;
        l->size = 1;
        return;
    }
    t->nxt = l->first;
    l->first->pre = t;
    l->first = t;
    l->size ++;
}

void dll_add_last(pdll l, T v) {
    pdln t = (pdln) malloc(sizeof(sdln));
    t->val = v;
    t->pre = NULL;
    t->nxt = NULL;
    if (l->size == 0) {
        l->first = t;
        l->last = t;
        l->size = 1;
        return;
    }
    t->pre = l->last;
    l->last->nxt = t;
    l->last = t;
    l->size ++;
}

void dll_remove_first(pdll l) {
    pdln t = NULL;
    if (l->first == NULL) return;
    if (l->first == l->last) {
        free(l->first);
        l->first = NULL;
        l->last = NULL;
        l->size = 0;
        return;
    }
    t = l->first->nxt;
    t->pre = NULL;
    free(l->first);
    l->first = t;
    l->size --;
}

void dll_remove_last(pdll l) {
    pdln t = NULL;
    if (l->last == NULL) return;
    if (l->first == l->last) {
        free(l->first);
        l->first = NULL;
        l->last = NULL;
        l->size = 0;
        return;
    }
    t = l->last->pre;
    t->nxt = NULL;
    free(l->last);
    l->last = t;
    l->size --;
}

T* dll_convert_to_array(pdll l) {
    T* arr = NULL;
    int arr_index = 0;
    pdln travel = NULL;
    pdln t1 = NULL, t2 = NULL;
    if (l == NULL || l->size == 0) return arr;
    arr = (T*) malloc(sizeof(T) * l->size);
    travel = l->first;
    while (travel != NULL) {
        arr[arr_index ++] = travel->val;
        travel = travel->nxt;
    }
    t1 = l->first;
    while (t1 != NULL) {
        t2 = t1->nxt;
        free(t1);
        t1 = t2;
    }
    free(l);
    return arr;
}

void dll_print(pdll l) {
    pdln t = l == NULL ? NULL : l->first;
    while (t != NULL) {
        printf("%d ", t->val);
        t = t->nxt;
    }
    printf("\r\n");
}

void dll_free_all(pdll l) {
    pdln t1 = l->first, t2 = NULL;
    while (t1 != NULL) {
        t2 = t1->nxt;
        free(t1);
        t1 = t2;
    }
    free(l);
}

char* simplifyPath(char* p) {
    pdll l = dll_init();
    int pn = 0, i = 0, sti = 0, len = 0, ai = 0;
    char c = '\0', *ans = NULL; 
    pdln n = NULL;
    while (1) {
        c = p[i ++];
        if (c == '\0') break;
        if (c == '/') {
            if (len == 2 && p[sti] == '.' && p[sti+1] == '.') {
                dll_remove_last(l);
            } else if (len != 0 && ! (len == 1 && p[sti] == '.')) {
                dll_add_last(l, sti);
            }
            sti = i;
            len = 0;
            continue;
        }
        len ++;
    }
    if (len == 2 && p[sti] == '.' && p[sti+1] == '.') {
        dll_remove_last(l);
    } else if (len != 0 && ! (len == 1 && p[sti] == '.')) {
        dll_add_last(l, sti);
    }
    pn = i;
    ans = (char*) malloc(sizeof(char) * pn);
    n = l->first;
    while (n != NULL) {
        i = n->val;
        ans[ai ++] = '/';
        while (1) {
            c = p[i++];
            if (c == '\0' || c == '/') break;
            ans[ai ++] = c;
        }
        n = n->nxt;
    }
    ans[ai ++] = '\0';
    if (l->first == NULL) {
        ans[0] = '/';
        ans[1] = '\0';
        return ans;
    }
    return ans;
}

int main() {
    char* p = "/home//foo/";
    char* a = simplifyPath(p);
    printf("answer is %s\r\n", a);
    free(a);
    return 0;
}


Python Solution: github

#coding=utf-8

'''
    url: leetcode.com/problems/simplify-path/
    @author:     zxwtry
    @email:      zxwtry@qq.com
    @date:       2017年4月16日
    @details:    Solution: 65ms 36.88%
'''

class Solution(object):
    def simplifyPath(self, p):
        """
        :type p: str
        :rtype: str
        """
        ps = p.split("/")
        l = []
        for s in ps:
            if s == "": continue
            if s == ".": continue
            if s == "..": 
                if len(l) > 0: l.pop()
                continue
            l.append(s)
        if len(l) == 0:
            return "/"
        ans = ""
        for s in l:
            ans += "/"
            ans += s
        return ans

if __name__ == "__main__":
    p = "/"
    print(Solution().simplifyPath(p))


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值