Insistir en un nuevo nombre de archivo

19

En tiempo de ejecución, sigue solicitando una línea de entrada hasta que la entrada del usuario no sea el nombre de un archivo o directorio existente u otro elemento del sistema de archivos, en relación con el directorio de trabajo actual. Luego devuelva / imprima el último nombre de archivo ingresado. Puede suponer que todas las entradas del usuario serán nombres de archivo válidos.

Pseudocódigo 1

myform = new form("GUI")
myform.mytxt = new editfield("")
myform.ok = new button("OK")
repeat
  waitfor(myform.ok,"click")
until not filesystem.exists(myform.mytxt.content)
return(myform.mytxt.content)

Pseudocódigo 2

LET TEXT = "."
WHILE HASFILE(TEXT) DO
  TEXT = PROMPT("")
ENDWHILE
RETURN TEXT

Ejemplos de entrada del usuario que provocarán una nueva solicitud cuando esté en TIO:

.
..
.env.tio
/
/bin/[
/lost+found

Ejemplos de entrada del usuario que regresará cuando esté en TIO:

...
env.tio
../../bin/]
/lost/found
Adán
fuente
Soy bastante nuevo en el código de golf aquí y parece que no puedo encontrar ninguna información sobre lo que cuenta como una solución. ¿Debo incluir la función main () para los idiomas que lo requieren en un programa, o puede ser parte del encabezado? ¿Pueden las declaraciones de importación ser parte del encabezado en TIO, o deben ser parte del código y contar contra el recuento de bytes? Por ejemplo, tengo esta solución: goo.gl/8RWNgu pero no estoy seguro de si los bytes serían legítimos.
Makotosan
2
@Makotosan Tanto las funciones como los programas completos están bien, aunque en el caso de las funciones deben ser reutilizables. Las importaciones generalmente deben incluirse en el recuento de bytes.
Martin Ender

Respuestas:

7

Lote, 37 bytes

@set/ps=
@if exist %s% %0
@echo %s%

(Por alguna razón, Windows 10 actual CMD.EXEcorrompe el título cuando ejecuta el %0.)

Neil
fuente
7

Mathematica, 33 28 bytes

f:=Input[]/._?FileExistsQ:>f

Esto supone el entorno del cuaderno de Mathematica donde podemos consultar la entrada del usuario con Input[]. La entrada del usuario debe ser un literal de cadena real , por ejemplo, en "ab/cd.ef"lugar de solo ab/cd.ef. Lo bueno es que la entrada puede ser una expresión arbitraria de Mathematica que calcula la cadena de entrada.

Esto define un símbolo fque, cuando se evalúa, realiza el cálculo requerido y, en última instancia, se evalúa hasta la primera entrada de usuario inexistente. Es esencialmente una función nular, donde no tenemos que incluir...[] para llamarla.

También podemos guardar un montón de bytes sobre una Ifexpresión tradicional haciendo uso del operador de sustitución de patrones /..

Martin Ender
fuente
Esto falla si el usuario ingresa lo mismo dos veces
Lukas Lang
@ Mathe172 Buena captura, muy mal, entonces tendré que seguir el ciclo aburrido.
Martin Ender
Resulta que no, e incluso es un byte más corto. :)
Martin Ender
7

Perl 5 -ln , 12 10 bytes

-2 bytes gracias a @DomHastings

#!/usr/bin/perl -ln
-e||1/!say

Pruébalo en línea!

Ton Hospel
fuente
1
Creo que -efunciona sin especificar $_, podría no funcionar para algunos casos, aunque supongo ...
Dom Hastings
@DomHastings Debería funcionar en todos los casos. Está documentado que $ _ se usa cuando no hay argumento para -e.
tubería
@DomHastings Gracias. Por alguna razón pensé que -eera una excepción, pero por supuesto que no lo es
Ton Hospel
4

Bash, 29

read f
[ -e $f ]&&$0||echo $f
Trauma digital
fuente
@ Adám No estoy seguro de por qué no funciona en TIO. Es suficiente decir que si lo guarda como un archivo de script y lo ejecuta, creo que funciona como se esperaba
Digital Trauma
1
@ Adám Esto funciona, el problema que tuvo fue que el programa estaba tratando de llamar .code.tioque contiene el cuerpo del script, pero no hay información sobre cómo ejecutarlo. Sin embargo, no estoy seguro de si hay una buena manera de evitar el shebang o si este script debe estar en tu camino.
FryAmTheEggman
2
Puede sortear ambos (a costa de dos bytes) cambiando $0a . $0. Pruébalo en línea! . Dado que .utiliza nombres de ruta relativos y el shell actual.
Chris
1
¿Qué piensa *como entrada?
Toby Speight
4

PowerShell 2 (hasta 6), 35 bytes

while(Test-Path($x=Read-Host)){};$x

Read-Hostespera la entrada (si se le da una cadena como parámetro, usa la cadena como indicador). Si la entrada proporcionada es un nombre de archivo (o nombre de carpeta) para uno que existe, se Test-Pathdevuelve $true, y el bloque de no hacer nada se {}ejecuta y vuelve a solicitar la entrada. Si se Test-Pathdevuelve $falseporque la entrada no es un archivo o carpeta existente, el bloque de no hacer nada no se ejecuta y se imprime el nombre de la entrada.

Jeff Zeitlin
fuente
1
Bienvenido a PPCG!
Martin Ender
No necesita el punto y coma después de {} para guardar un byte.
Veskah
@Veskah - Lo hice en PS2, y no rompe PS3 +
Jeff Zeitlin
Ah, mi mal. No lo
probé
4

C (gcc) , 62 bytes

main(){char b[99];while(scanf("%s",b)&&!access(b,0));puts(b);}

Pruébalo en línea!

main(){
    char b[99]; // Declare buffer b
    while (scanf("%s",b)&&!access(b,0));    // Take one line of input, and test if file is accessible (exists)
    puts (b);   // If doesn't exist, loop ends and print file
}
Kona ártica
fuente
Bienvenido a PPCG! Puede usar while(gets(b),!access(b,0));para guardar 7 bytes.
Dennis
3

Funky , 40 bytes

tryfor)io.open(s=io.read())catchprint(s)

En un verdadero estilo funky, esto utiliza palabras clave atascadas entre sí, paréntesis inigualables y palabras clave implícitas. Limpiado, esto se ve así:

try{
    while(true){
        s = io.read()
        io.open(s)
    }
}catch(e){
    print(s)
}

Descompostura

try                                     // Try statement, this one is expected to fail.
   for)                                 // for) is a for loop with no arguments, which is functionally equivilent to a while(true) loop, much like for(;;)
       io.open(                         // Try to open a file relative to the CWD. If this fails to find a file, it will throw an error and escape the try/catch
               s=io.read()              // Read a line from STDIN and store it as s, this will still pass it to the arguments of the call.
                          )
                           catch        // When io.open fails
                                print(s)// Print out the last entered line.
Un taco
fuente
3

Haskell , 76 bytes

import System.Directory
f=do x<-getLine;b<-doesPathExist x;last$pure x:[f|b]

Pruébalo en línea!

Devuelve IO xdonde xestá el nombre ingresado del archivo que no existe.

Sin golf

import System.Directory

insist = do { file <- getLine;
              exists <- doesPathExist file;
              if exists then insist else pure file }
totalmente humano
fuente
3

R , 66 51 bytes

while((s=readline())%in%list.files(a=T)){};print(s)

-15 bytes gracias a plannapus

Ejecuta un bucle potencialmente infinito, donde en cada iteración

  1. Se almacena una sola línea de entrada del usuario en la variable s
  2. Verificamos si la entrada está en la lista de nombres de archivo para el directorio de trabajo (la a=Topción paralist.files() debe usarse para recoger cosas como.. )
  3. Si sestá en esa lista, pasamos a la siguiente iteración; si no, rompemos el ciclo e imprimimos s.
Duckmayr
fuente
¿Qué tal acortarlo a while((s=readline())%in%list.files(a=T)){};print(s)?
plannapus
@plannapus ¡Gran idea! Incorporado.
Duckmayr
De nada. Además, no lo pensé de inmediato, pero funciona list.filesy dirson sinónimos, por lo que puede reemplazarlo diraquí.
plannapus
también podría reemplazar readline()conscan(,'')
JAD
Y printconcat
JAD
3

Python 3 , 55 bytes

import glob
s="."
while glob.glob(s):s=input()
print(s)

Pruébalo en línea!

-4 bytes gracias a ManfP
-6 bytes gracias a Rick Rongen

Hiperneutrino
fuente
2
@ Adám terrible mala interpretación, lo siento
HyperNeutrino
Podrías reemplazar el primero input()con"."
ManfP
1
import osy os.path.existses tres bytes más corto.
Jonathan Allan
1
Rick Rongen sugirió import globy while glob.glob(s):...en una edición.
Martin Ender
@MartinEnder gracias por decirme :)
HyperNeutrino
3

C #, 101 bytes

()=>{var s="";try{for(;;System.IO.File.GetAttributes(s=System.Console.ReadLine()));}catch{}return s;}

Para cada uno de los 4 valores de retorno válidos:

Sin golf

() =>
{
    var s = "";
    try
    {
        for(;; System.IO.File.GetAttributes(s = System.Console.ReadLine()));
    }
    catch {}
    return s;
}

Explicación

se basa en el hecho de que File.GetAttributes () produce una excepción si el objeto del sistema de archivos especificado en su argumento no existe.

Ricardo II
fuente
2

Powershell 3.0, 75 bytes

$x=1;while($x){$i=Read-Host;$x=Test-Path("$PSScriptRoot\$i")};Write-Host $i

Primer intento; Estoy seguro de que hay algunas optimizaciones que podría hacer.

Una forma ligeramente más legible:

$x=1;                                                                       # Make sure we enter our while loop.
     while($x){                                                             # While we keep getting file names,                   
               $i=Read-Host;                                                # Get input from the user
                            $x=Test-Path("$PSScriptRoot\$i")};              # Combine our path with the user input, and see if it already exists.
                                                              Write-Host $i # Return the final (valid) file name.
Arkitekt
fuente
¿No funcionaría incluso sin él $PSScriptRoot\?
Adám
Bienvenido a PPCG! Algunos campos de golf rápidos: en su forlugar, puede usar un bucle, que le permite mover la inicialización al constructor del bucle for($x=1;$x){...}. En segundo lugar, puede deshacerse de él Write-Hostya que hay un implícito Write-Outputen la finalización del programa para cualquier cosa que quede en la tubería, por lo que basta con irse de $iallí.
AdmBorkBork
Vea mi solución a continuación; He reducido a la mitad su número de bytes.
Jeff Zeitlin
@ Adám: ¡Quizás! En realidad no lo había considerado. : P AdmBorkBork ¡Gracias! Pasé mucho tiempo al acecho. Esas son buenas ideas; la salida implícita ni siquiera se me pasó por la mente ...
Arkitekt
2

Java 9, 87 bytes

v->{String s;for(;new java.io.File(s=System.console().readLine()).exists(););return s;}

Sin golf

La JVM de TIO aparentemente no tiene sistemaConsole , por lo que no es comprobable allí (ver System.console()).

import java.util.function.*;
class Main {
  public static void main(String[] args) {
    Function<Void,String> f =


v->{
  String s;
  for(;new java.io.File(s=System.console().readLine()).exists(););
  return s;
}


;
    System.out.println(f.apply(null));
  }
}
Olivier Grégoire
fuente
2

JavaScript (Node.js) , 158 118 bytes

require('readline').createInterface({input:process.stdin}).on('line',s=>require('fs').existsSync(s)||--console.log(s))

Pruébalo en línea!

Gracias a @ ConorO'Brien por proponer una versión más corta. Objetos en línea en lugar de usar consts y utilizar la condición de salida de error en lugar de salir explícitamente.

Makotosan
fuente
1
Buena respuesta hasta ahora, pero hay espacio para el potencial. Puede aprovechar este enfoque de varias maneras: puede omitir ambos consty también puede reemplazar cada variable con su definición. Luego, en lugar de usar s=>{if(...){...}}, puedes usar s=>require('fs').existsSync(s)||process.exit(console.log(s)). Además, puede salir con un error, por lo que puede escribir el lambda como s=>require('fs').existsSync(s)||--console.log(s). Pruébalo en línea!
Conor O'Brien
¡Grandes ideas! ¡Gracias!
Makotosan
1

Limpio , 100 94 bytes

import System.IO,System.File
Start w#(s,w)=evalIO getLine w
#(b,w)=fileExists s w
|b=Start w=s

Pruébalo en línea!

versión de una sola expresión:

import System.IO,System.File
Start w=(\(s,v)=(\(b,w)|b=Start w=s)(fileExists s v))(evalIO getLine w)

Pruébalo en línea!

Οurous
fuente
1

Perl 6, 39 bytes

my$f=".";while $f.IO.e {$f=get};say $f;

Esto funciona en REPL, pero no parece funcionar correctamente en TIO.

Mattchuranu
fuente
¿Qué pasa con say first !*.IO.e,lines(23 bytes)?
nwellnhof
Lo anterior probablemente se bloquea indefinidamente cuando se ejecuta en la línea de comando, pero algo así {}while ($_=get).IO.e;.saydebería funcionar.
nwellnhof
1

PHP, 43 bytes

<?for(;file_exists($f=readline()););echo$f;

Ejecutar como CLI. Muy fácil de entender.

tsh
fuente
1

APL (Dyalog) , 17 bytes

{⍞}⍣{~⎕NEXISTS⍺}⍬

Pruébalo en línea!

Uriel
fuente
Devuelve la segunda entrada no existente (en the_prev_wasnt_filenamelugar de env.tio). Cambie y luego puede deshacerse de él '.'también.
Adám
1

Adjunto , 35 bytes

{While[FileExists[x:=Prompt[]],0]x}

Pruébalo en línea!

Soluciones alternativas

35 bytes: {If[FileExists[x:=Prompt[]],$[],x]} función recursiva.

37 bytes:, {NestWhile[p:=Prompt,p[],FileExists]} función iterativa.

Conor O'Brien
fuente
1

Min , 38 bytes

"." :a (a exists?) ("" ask @a) while a

Deja el último nombre de archivo ingresado en la pila.

Explicación

"."         ; Put . on the stack. Every directory should contain this...
:a          ; Assign to a
(a exists?) ; A quot that checks if a exists in current directory
("" ask @a) ; Read line from stdin, assign to a
while       ; Do the second quote while the first leaves true on the stack
a           ; Leave a on the stack
Panda0nEarth
fuente
0

SmileBASIC, 27 bytes

INPUT S$EXEC!CHKFILE(S$)?S$
12Me21
fuente