Permissões de arquivo

26

Permissões de arquivo

Adaptado da pergunta de resposta livre UIL - Computer Science Programming "Carla" para o Distrito de 2018.

Introdução

Nos sistemas operacionais do tipo UNIX, cada arquivo, diretório ou link é "de propriedade" de um "usuário", membro de um "grupo" e possui determinadas "permissões" representadas por uma cadeia de dez caracteres, como " drwxrwxrwx ". O primeiro caractere é 'd', '-' ou 'l' (diretório, arquivo ou link), seguido por três conjuntos de valores "rwx", indicando permissões "ler, escrever, executar". O primeiro conjunto são os direitos do usuário, o meio define os direitos do grupo e o terceiro os direitos de todos os demais sobre esse objeto.

A permissão negada para qualquer um desses direitos é representada por um '-' no lugar de 'r', 'w' ou 'x'. Por exemplo, uma sequência de permissões de diretório de exemplo seria "drwxr - r--", indicando direitos completos de diretório para o usuário, mas direitos "somente leitura" para o membro do grupo e todos os outros.

Cada combinação "rwx" também pode ser representada por um valor octal (0-7) com o bit mais significativo representando permissão de leitura, o próximo bit mais significativo representando permissão de gravação e o bit menos significativo representando permissão de execução.

Desafio

Dada uma sequência de código de quatro caracteres composta por um caractere: 'D', 'F' ou 'L', seguida por um valor inteiro octal de três dígitos, como 664, gera a sequência de 10 caracteres resultante que representa o valor da permissão indicado.

Entrada

Seu programa ou função pode ler a entrada do padrão em (quatro caracteres serão inseridos, opcionalmente seguidos por uma nova linha) ou receber a entrada como argumento.

Seu programa pode aceitar entradas em maiúsculas ou minúsculas, mas deve ser consistente (todas as entradas são maiúsculas ou todas as minúsculas).

Saída

Seu programa deve imprimir a sequência de dez caracteres resultante que representa o valor da permissão indicado no formato exato especificado acima. O espaço em branco restante é permitido.

Casos de teste

Entrada: F664Saída: -rw-rw-r--
Entrada: D775Saída: drwxrwxr-x
Entrada: L334Saída: l-wx-wxr--
Entrada: F530Saída: -r-x-wx---
Entrada: D127Saída:d--x-w-rwx

Pontuação e Regras

Billylegota
fonte
Espere o que, perguntou ontem e a resposta já foi aceita? Isso significa que não são mais esperadas respostas ou o quê?
Nit
1
@Nit Mais respostas são sempre bem-vindas, independentemente de uma resposta ser aceita.
Isaacg
1
@Nit Eu estava no celular e tentando diminuir o voto de uma resposta não relacionada (que foi removida desde então). Apertei acidentalmente o botão de resposta com o dedo gordo. Como não consegui descobrir como aceitar, mudei a resposta aceita para a mais curta a partir de agora.
precisa saber é o seguinte
2
@ Quero dizer ... ele aceitou uma resposta de Dennis, então, honestamente, pode estar correto.
Urna de polvo mágico

Respostas:

7

Geléia , 19 bytes

“rwx“-”Œp⁺;Ṁ⁾f-yị@~

Experimente online!

Como funciona

“rwx“-”Œp⁺;Ṁ⁾f-yị@~  Main link. Argument: s (string)

“rwx“-”              Set the return value to ["rwx, "-"].
       Œp            Take the Cartesian product, yielding ["r-", "w-", "x-"].
         ⁺           Take the Cartesian product, yielding
                     ["rwx", "rw-", "r-x", "r--", "-wx", "-w-", "--x", "---"].
          ;Ṁ         Append the maximum of s (the letter).
            ⁾f-y     Translate 'f' to '-'.
                  ~  Map bitwise NOT over s.
                     This maps the letter to 0, because it cannot be cast to int,
                     and each digit d to ~d = -(d+1).
                ị@   Retrieve the results from the array to the left at the indices
                     calculated to the right.
                     Indexing is modular and 1-based, so the letter from s is at
                     index 0, "---" at index -1, ..., and "rwx" at index -8.
Dennis
fonte
16

bater, 59 53 bytes

chmod ${1:1} a>a;stat -c%A a|sed s/./${1:0:1}/|tr f -

Ferramenta certa para o trabalho?

Agradecemos a Dennis por salvar 5 bytes e o HTNW por salvar um.

Experimente online!

chmod ${1:1} a>a;  # call chmod with the input with its first character removed
                   # note that the redirection creates the file a *before* the
                   #   chmod is run, because of the way bash works
stat -c%A a|       # get the human readable access rights
sed s/./${1:0:1}/  # replace the first character with the first char of input
|tr f -            # transliterate, replacing f with -
Maçaneta da porta
fonte
Bem, isso foi rápido. Certamente a ferramenta certa para o trabalho.
precisa saber é o seguinte
chmod ${1:1} a>a;stat -c%A a|sed "s/-/\L${1:0:1}/;s/f/-/"salva dois bytes.
Dennis
Saindo do @Dennis, acho que você pode raspar mais um ao trinvés de y:chmod ${1:1} a>a;stat -c%A a|sed s/./\\L${1:0:1}/|tr f -
HTNW 29/04
2
É legítimo supor que não há arquivo ae que o usuário tenha permissão para criá-lo ou que haja um arquivo agravável pelo usuário? Porque se houver um arquivo apertencente a rootcom permissões 700, isso não deve funcionar.
NoOneIsHere
2
@NoOneIsHere Embora as permissões em particular nunca tenham surgido na discussão, a comunidade decidiu que a criação de arquivos temporários no diretório atual é permitida por padrão . Por extensão, podemos assumir que é possível.
Dennis
10

Python 2 , 78 bytes

lambda a,*b:[a,'-'][a=='f']+''.join('-r'[x/4]+'-w-w'[x/2]+'-x'[x%2]for x in b)

Toma entrada como um caractere e três polegadas.
Experimente online!

Explicação

[a,'-'][a=='f']pega o caractere de entrada ou -, se o caractere for f.
'-r'[x/4]+'-w-w'[x/2]+'-x'[x%2]é essencialmente uma conversão octal para obter a rwxstring.


fonte
5

Perl 5 com-p , 37 bytes

s/\d/(<{-,r}{-,w}{-,x}>)[$&]/ge;y;f;-

Recebe entrada em minúsculas.

Experimente online!

Dom Hastings
fonte
5

Retina 0.8.2 , 43 bytes

\d
$&r$&w$&x
f|[0-3]r|[0145]w|[0246]x
-
\d

Experimente online! O link inclui casos de teste. Recebe entrada em minúsculas. Explicação:

\d
$&r$&w$&x

Triplicar cada dígito, com o sufixo com r, we x.

f|[0-3]r|[0145]w|[0246]x
-

Altere todas as letras incorretas para -s.

\d

Exclua os dígitos restantes.

Neil
fonte
4

Retina , 51 bytes

f
-
0
---
1
--x
2
-w-
3
-wx
4
r--
5
r-x
6
rw-
7
rwx

Experimente online!

Não faço ideia de como usar o Retina, então, deixe-me saber como fazer isso melhor. Imaginei que tentaria aprender pelo menos um idioma que não é Pyth.

Explicação:

Substitua fpor -(deixando de linalterado) e substitua cada dígito pelo apropriado rwx.


fonte
: / Eu posso chegar tão longe como este , mas não mais. e a maneira inteligente é super ungolfy
somente ASCII
Seria muito Golfier com algum tipo de ternário / lógica / ou adicionar e operadores de acabamento
ASCII-only
@ ASCII-only Sua idéia foi muito bom, eu usei-o para esta resposta :)
Leo
4

JavaScript (ES6), 63 bytes

Espera a sequência de entrada em minúsculas.

s=>s.replace(/\d|f/g,c=>1/c?s[c&4]+s[c&2]+s[c&1]:'-',s='-xw-r')

Experimente online!

Comentado

s => s.replace(   // replace in the input string s
  /\d|f/g, c =>   //   each character c which is either a digit or the letter 'f'
    1 / c ?       //   if c is a digit:
      s[c & 4] +  //     append '-' or 'r'
      s[c & 2] +  //     append '-' or 'w'
      s[c & 1]    //     append '-' or 'x'
    :             //   else:
      '-',        //     just replace 'f' with '-'
  s = '-xw-r'     //   s holds the permission characters
)                 // end of replace()
Arnauld
fonte
4

Carvão , 27 bytes

FS≡ιdιlιf¦-⭆rwx⎇§↨⁺⁸Iι²⊕λκ-

Experimente online! Link é a versão detalhada do código. Explicação:

 S                          Input string
F                           Loop over characters
   ι                        Current character
  ≡                         Switch
    d                       Literal `d`
     ι                      Implicitly print current character
      l                     Literal `l`
       ι                    Implicitly print current character
        f                   Literal `f`
         ¦                  (Separator between string literals)
          -                 Implicitly print literal `-`
                            Implicit default case
            rwx             Literal `rwx`
           ⭆                Map over characters
                     ι      Input character
                    I       Cast to integer
                   ⁸        Literal 8
                  ⁺         Sum
                      ²     Literal 2
                 ↨          Base conversion
                        λ   Inner index
                       ⊕    Incremented
                §           Index into base conversion
                         κ  Inner character
                          - Literal `-`
               ⎇            Ternary
                            Implicitly print
Neil
fonte
4

Haskell , 84 83 81 bytes

f 'f'='-'
f y=y
t#n=f t:((\x->["-r"!!div x 4,"-w-w"!!div x 2,"-x"!!mod x 2])=<<n)

Experimente online!

Acabou sendo bastante semelhante em conceito à resposta Python 2 do Mnemonic. f cria o tipo de arquivo, o restante são as permissões de obtenção do número octal. Este realmente me fez desejar & foi um bit a bit e operador incluído no prelúdio.

aoemica
fonte
2
Você pode usar em divvez de quot.
Nimi
4

Java 8, 100 bytes

s->s.replaceAll("(\\d)","$1r$1w$1x").replaceAll("f|[0-3]r|[0145]w|[0246]x","-").replaceAll("\\d","")

Experimente online.

Porto da resposta Retina de @Neil .

Explicação:

s->                                 // Method with String as both parameter and return-type
  s.replaceAll("(\\d)","$1r$1w$1x") //  Replace every digit `d` with 'drdwdx'
   .replaceAll("f                   //  Replace every "f",
                |[0-3]r             //  every "0r", "1r", "2r", "3r",
                |[0145]w            //  every "0w", "1w", "4w", "5w",
                |[0246]x",          //  and every "0x", "2x", "4x", "6x"
               "-")                 //  with a "-"
   .replaceAll("\\d","")            //  Remove any remaining digits
Kevin Cruijssen
fonte
Isso é esperto! ;)
Olivier Grégoire
@ OlivierGrégoire Bem, principalmente porque economiza na declaração de retorno e loops. Pena que três indivíduos .replaceAllainda têm menos bytes do que um loop com .replaceAlle adicionados returne String-array. Mas é claro que o crédito é para Neil , que é a resposta Retina que eu usei como base para a porta.
Kevin Cruijssen
3

Gelatina , 21 bytes

Ḣ⁾f-yɓOBṫ€4a“rwx”o”-ṭ

Um programa completo de impressão em STDOUT. (Como um link monádico, o valor retornado é uma lista que contém um caractere e uma lista de três listas de caracteres.)

Experimente online! Ou veja a suíte de testes .

Quão?

Ḣ⁾f-yɓOBṫ€4a“rwx”o”-ṭ | Main Link: list of characters
Ḣ                     | head & pop (get the 1st character and modify the list)
 ⁾f-                  | list of characters = ['f', '-']
    y                 | translate (replacing 'f' with '-'; leaving 'd' and 'l' unaffected)
     ɓ                | (call that X) new dyadic chain: f(modified input; X)
      O               | ordinals ('0'->48, '1'->59, ..., '7'->55 -- notably 32+16+value)
       B              | convert to binary (vectorises) (getting three lists of six 1s and 0s)
        ṫ€4           | tail €ach from index 4 (getting the three least significant bits)
           “rwx”      | list of characters ['r', 'w', 'x']
          a           | logical AND (vectorises) (1s become 'r', 'w', or 'x'; 0s unaffected)
                 ”-   | character '-'
                o     | logical OR (vectorises) (replacing any 0s with '-'s)
                   ṭ  | tack (prepend the character X) 
                      | implicit print (smashes everything together)
Jonathan Allan
fonte
3

Perl 6 -p , 37 bytes

s:g[\d]=[X~]('-'X <r w x>)[$/];s/f/-/

Experimente online!

Solução Perl 5 do Porto de Dom Hastings.

Nwellnhof
fonte
3

Retina , 38 bytes

Inspirado por um comentário apenas do ASCII .

\d
---$&*
---____
r--
--__
w-
-_
x
f
-

Experimente online!

A ideia é converter cada dígito em unário (o dígito unário padrão na Retina é _) com três iniciais -e, em seguida, converter dígitos binários do mais para o menos significativo.

Leo
fonte
2

Python 3 , 71 bytes

lambda s:("-"+s)[s[0]!="f"]+stat.filemode(int(s[1:],8))[1:]
import stat

Experimente online!

O Python 3.3+ tem um built-in para isso, embora devido à necessidade de importação e diferenças no formato de entrada esperado, ele não seja muito favorável ao golfe.

Kirill L.
fonte
2

Tcl , 139 bytes

proc P s {join [lmap c [split $s ""] {expr {[regexp \\d $c]?"[expr $c&4?"r":"-"][expr $c&2?"w":"-"][expr $c&1?"x":"-"]":$c==f?"-":$c}}] ""}

Experimente online!


Tcl , 144 bytes

proc P s {join [lmap c [split $s ""] {expr {[regexp \\d $c]?[list [expr $c&4?"r":"-"][expr $c&2?"w":"-"][expr $c&1?"x":"-"]]:$c==f?"-":$c}}] ""}

Experimente online!

Tcl , 149 bytes

proc P s {join [lmap c [split $s ""] {if [regexp \\d $c] {list [expr $c&4?"r":"-"][expr $c&2?"w":"-"][expr $c&1?"x":"-"]} {expr {$c==f?"-":$c}}}] ""}

Experimente online!

Tcl , 150 bytes

proc P s {join [lmap c [split $s ""] {if [regexp \\d $c] {set v [expr $c&4?"r":"-"][expr $c&2?"w":"-"][expr $c&1?"x":"-"]} {expr {$c==f?"-":$c}}}] ""}

Experimente online!

Tcl , 180 bytes

proc P s {join [lmap c [split $s ""] {if [regexp \\d $c] {[set R regsub] (..)1 [$R (.)1(.) [$R 1(..) [$R -all 0 [format %03b $c] -] r\\1] \\1w\\2] \\1x} {expr {$c==f?"-":$c}}}] ""}

Experimente online!

Ainda muito não-destruído!

sergiol
fonte
2

Java (JDK 10) , 118 bytes

s->{var r=s[0]=='f'?"-":""+s[0];var z="-xw r".split("");for(int i=0;++i<4;)r+=z[s[i]&4]+z[s[i]&2]+z[s[i]&1];return r;}

Experimente online!

Créditos

Olivier Grégoire
fonte
2
Quando você coloca a entrada como minúscula fdl, pode alterar var r=s[0]<70?"d":s[0]<72?"-":"l";para var r=s[0]=='f'?"-":s[0]+"";para salvar 6 bytes. Além disso, .toCharArray()pode ser .split("")para salvar um adicional de 4 bytes.
Kevin Cruijssen
2
@KevinCruijssen Sua idéia me fez economizar 13 bytes, não 10 (já que eu poderia remover ""+posteriormente para "converter" a charem a String);) Obrigado!
Olivier Grégoire
2

Excel, 224 bytes

=IF(LEFT(A1,1)="f","-",LEFT(A1,1))&CHOOSE(MID(A1,2,1)+1,"---","--x","-w-","-wx","r--","r-x","rw-","rwx")&CHOOSE(MID(A1,3,1)+1,"---","--x","-w-","-wx","r--","r-x","rw-","rwx")&CHOOSE(MID(A1,4,1)+1,"---","--x","-w-","-wx","r--","r-x","rw-","rwx")

Feito em 4 etapas:

IF(LEFT(A1,1)="f","-",LEFT(A1,1))    Replace "f" with "-".

E 3 vezes:

CHOOSE(MID(A1,2,1)+1,"---","--x","-w-","-wx","r--","r-x","rw-","rwx")

Tentando ser mais inteligente, adiciona 25 bytespor conjunto de direitos, 75 no total:

IF(INT(MID(A1,2,1))>3,"r","-")&IF(MOD(MID(A1,2,1),4)>1,"w","-")&IF(ISODD(MID(A1,2,1)),"x","-")
Wernisch
fonte
2

05AB1E , 34 27 bytes

ćls8βbvyi…rwx3*Nèë'-}J'f'-:

Experimente online!

Golfed down 7 bytes por @MagicOctopusUrn


ć                           # Remove head from string.
 ls                         # Lowercase swap.
   8βb                      # Octal convert to binary.
      vy                    # For each...
        i        ë  }
         …rwx3*Nè           # If true, push the correct index of rwx.
                  '-        # Else push '-'.
                     J      # Repeatedly join stack inside the loop.
                      'f'-: # Repeatedly replace 'f' with '-' inside the loop.
Geno Racklin Asher
fonte
ćls8βbvyi…rwx3*Nèë'-}J'f'-:por 7 menos ...
Magic Octopus Urn
Basicamente, apenas uma ordem diferente usando instruções if e, em vez de remover o f, estou apenas substituindo todos fna string final por -.
Magic Octopus Urn
i <CODE FOR TRUE> ë <CODE FOR FALSE> }
Urna de polvo mágico
@MagicOctopusUrn Nice!
Geno Racklin Asher
1

Python 2 , 238 bytes

lambda m,r=str.replace,s=str.split,j="".join,b=bin,i=int,z=str.zfill,g=lambda h,y:y if int(h)else "-":r(m[0],"f","-")+j(j([g(z(s(b(i(x)),"b")[1],3)[0],"r"),g(z(s(b(i(x)),"b")[1],3)[1],"w"),g(z(s(b(i(x)),"b")[1],3)[2],"x")])for x in m[1:])

Experimente online!

Eu tinha assumido que isso seria uma gota no balde, mas eu estava realmente errado. Provavelmente deveria ter percebido que um lambda não era a melhor ideia em algum momento.

LyricLy
fonte
: | muitos buildins = muito tempo
somente ASCII
1

APL + WIN, 55 bytes

Solicita a sequência de entrada com caracteres iniciais minúsculos:

('dl-'['dlf'⍳↑t]),⎕av[46+(,⍉(3⍴2)⊤⍎¨⍕1↓t←⎕)×9⍴69 74 75]

Explicação:

9⍴69 74 75 create a vector of ascii character codes for rwx -46, index origin 1

1↓t←⎕ prompt for input and drop first character

,⍉(3⍴2)⊤⍎¨⍕ create a 9 element vector by concatenating the binary representation for each digit 

46+(,⍉(3⍴2)⊤⍎¨⍕1↓t←⎕)×9⍴69 74 75 multiply the two vectors and add 46

⎕av[.....] convert back from ascii code to characters, 46 being '-'

('dl-'['dlf'⍳↑t]), append first character from input swapping '-' for 'f'
Graham
fonte
1

J , 57 52 bytes

5 bytes salvos graças ao FrownyFrog!

-&.('-DLld'i.{.),[:,('-',:'rwx'){"0 1&.|:~1#:@}."."0

Experimente online!

Mais uma solução longa ... não sei como }trabalhar em verbos tácitos e é por isso que usei muito mais tempo {"0 1&.|:para a seleção.

Explicação:

@}. Largue o primeiro símbolo e

,.&.": converte o restante em uma lista de dígitos desimais

]:#: converta cada dígito em uma lista de dígitos binários (e limpe o garfo)

('-',:'rwx') cria uma tabela de 2 linhas e usa 0 para selecionar da primeira linha / 1 - da segunda

   '-',:'rwx'
---
rwx

{"0 1&.|:~ usa os dígitos binários para selecionar na tabela acima

[:, nivela o resultado

('d-l'{~'DFL'i.{.) formata o primeiro símbolo

, anexa o símbolo fisrt à lista de permissões

Galen Ivanov
fonte
1
A entrada já é uma string, você precisa1#:@}."."0
FrownyFrog
1
Isso parece funcionar: ('d-l'{~'DFL'i.{.)-&.('-DLld'i.{.)
FrownyFrog
@FrownyFrog Uso muito agradável i.e &.muito obrigado! A propósito, você pode me explicar como usar os }verbos select em tácito?
Galen Ivanov
1
2 2 2&#:`('-',:'rwx'"_)}@"."0@}.é exatamente o mesmo comprimento
FrownyFrog
No entanto ele não quebrar em 333:)
FrownyFrog
1

PHP, 68 bytes

<?=strtr(strtr($argn,[f=>_,___,__x,_w_,_wx,r__,r_x,rw_,rwx]),_,"-");

converte fem entrada minúscula em sublinhado e cada número octal em seu rwxequivalente, usando sublinhados em vez de hífens (para salvar a necessidade de aspas) e, em seguida, substitui o_ por- .

Execute como pipe -nFou experimente online .

Titus
fonte
1

C (gcc) , 109 104 bytes

Pelo menos C pode converter entrada octal .... :-)

Edit: eu percebi que o modificador de tamanho não era estritamente necessário, e que putchar()é menor queprintf() neste caso!

f(a,b){char*s="-xwr";scanf("%c%o",&a,&b);putchar(a-70?a:*s);for(a=9;~--a;putchar(s[(1&b>>a)*(a%3+1)]));}

Experimente online!

Original:

f(a,b){char*s="-xwr";scanf("%c%3o",&a,&b);putchar(a-70?a:*s);for(a=9;~--a;printf("%c",s[(1&b>>a)*(a%3+1)]));}

Experimente online!

ErikF
fonte