2012-04-05 51 views
19

Tôi đang cố gắng làm việc với một đường dẫn và thay thế thư mục chính bằng dấu ngã trong bash, Im hy vọng sẽ hoàn thành nó với ít chương trình bên ngoài khi cần thiết. Có cách nào để làm điều đó chỉ với bash. Tôi đã nhận đượcCó cách nào tốt để thay thế thư mục chính bằng dấu ngã trong bash không?

${PWD/#$HOME/\~} 

Nhưng điều đó không hoàn toàn đúng. Nó cần phải chuyển đổi:

/home/alice to ~ 
/home/alice/ to ~/ 
/home/alice/herp to ~/herp 
/home/alicederp to /home/alicederp 

Là một lưu ý quan tâm, heres cách nguồn bash làm nó khi chuyển đổi \w value in the prompt:

/* Return a pretty pathname. If the first part of the pathname is 
    the same as $HOME, then replace that with `~'. */ 
char * 
polite_directory_format (name) 
    char *name; 
{ 
    char *home; 
    int l; 

    home = get_string_value ("HOME"); 
    l = home ? strlen (home) : 0; 
    if (l > 1 && strncmp (home, name, l) == 0 && (!name[l] || name[l] == '/')) 
    { 
     strncpy (tdir + 1, name + l, sizeof(tdir) - 2); 
     tdir[0] = '~'; 
     tdir[sizeof(tdir) - 1] = '\0'; 
     return (tdir); 
    } 
    else 
    return (name); 
} 
+0

Đây không phải là bash, giống như mã C. Nhưng thay thế một chuỗi với hầu như không có bối cảnh là dễ bị lỗi. bạn có chắc chắn muốn tiếp tục như vậy không? – pizza

+1

Xin lỗi nếu điều này không rõ ràng. Mã C là một ví dụ về cách thực hiện. Bản thân nó bash như thế nào. bash là một chương trình được viết bằng C. Bây giờ tôi muốn làm điều tương tự trong ngôn ngữ bash. – Jake

+1

Bạn có thể cho chúng tôi biết kết quả đầu ra như bây giờ không? – birryree

Trả lời

7

Xem this unix.stackexchange answer:

Nếu bạn đang sử dụng bash thì dirs dựng sẵn có mong muốn hành vi:

dirs +0 
~/some/random/folder 

Điều đó có thể sử dụng mã C riêng của Bash mà bạn đã dán ở đó. :)

Và đây là cách bạn có thể sử dụng nó:

dir=...      # <- Use your own here. 
pushd "$dir" > /dev/null # Switch to the given directory; 
          # suppress output. 
dir_with_tilde=$(dirs +0) # Run "dirs" and save to variable. 
popd > /dev/null   # Switch back to where we were 
+1

Bạn có thể muốn' dirs + 0', nếu không khi sử dụng thư mục stack ('pushd foo') nó sẽ hiển thị thư mục gốc (ở cuối ngăn xếp) thay vì hiện tại. – dcoles

+0

Cảm ơn; sửa chữa. Lần tới, hãy chỉnh sửa trực tiếp. –

+0

Bạn có thể làm 'dir_with_tilde =" $ (cd "$ {dir}" && dirs +0) "' làm một lớp lót ... Nhưng, điều này không có tác dụng nếu thư mục không tồn tại, vì bạn không thể thay đổi thành thư mục không tồn tại. Bạn có thể đang xây dựng một đường dẫn để tạo và muốn đăng nhập theo cách thân thiện. –

12

Tôi không biết một cách để làm điều đó trực tiếp như một phần của một biến thay thế, nhưng bạn có thể làm điều đó như là một lệnh:

[[ "$name" =~ ^"$HOME"(/|$) ]] && name="~${name#$HOME}" 

Lưu ý rằng điều này không thực hiện chính xác những gì bạn yêu cầu: nó thay thế "/ home/alice /" với "~ /" hơn hơn "~". Đây là cố ý, vì có những nơi dấu gạch chéo có ý nghĩa quan trọng (ví dụ: cp -R ~ /backups có điều gì đó khác với cp -R ~/ /backups).

+3

Giải pháp này không hiệu quả đối với tôi, vì nó cắt mọi thứ sau "~". Ví dụ./home/alice/tài liệu được thay đổi thành "~", trong khi tôi muốn nó chỉ thay thế phần thư mục chính và trả về "~/documents". Rõ ràng, đây không phải là vấn đề đối với poster gốc. Tuy nhiên, tôi đã đưa ra 'name = $ (echo $ name | sed" s:^$ HOME: ~: ")', mà dường như làm những gì _I_ muốn. Chỉ nghĩ rằng tôi muốn chia sẻ, vì tôi đến đây lần đầu tiên khi tìm kiếm một giải pháp. – Steinar

+1

@Steinar: Nó sẽ làm những gì bạn muốn - phần '$ {name # $ HOME}' có '$ name' và loại bỏ' $ HOME' từ phía trước (tức là "/ tài liệu" trong ví dụ của bạn). Có thể bạn đã có lỗi đánh máy? –

+0

@GordonDavisson: Your're đúng, nó _does_ làm việc theo cách tôi muốn nó ... Tôi phải có một lỗi đánh máy khi kiểm tra nó ra. – Steinar

6

tôi đã thực hiện điều này với thay chuỗi đồng bằng ol bash :)

> echo $HOME 
/Users/fots 
> mypath="/Users/fots/some/cool/path" 
> echo ${mypath/$HOME/\~} 
~/some/cool/path 
+2

'mypath ="/Users/Users/fots "' dẫn đến '/ Users ~' vì sự thay thế lệnh của bạn không được neo vào trước đường dẫn, nhưng sẽ thay thế nó ở bất kỳ đâu trong chuỗi. 'mypath =" Users/fotssss "' dẫn đến '~ sss' –

Các vấn đề liên quan