stringtranslate.com

Flujos estándar

En programación de computadoras , los flujos estándar son canales de comunicación de entrada y salida [1] preconectados entre un programa de computadora y su entorno cuando comienza la ejecución. Las tres conexiones de entrada/salida (E/S) se denominan entrada estándar ( stdin ), salida estándar ( stdout ) y error estándar ( stderr ). Originalmente, la E/S se realizaba a través de una consola del sistema conectada físicamente (entrada a través del teclado, salida a través del monitor), pero las transmisiones estándar abstraen esto. Cuando un comando se ejecuta a través de un shell interactivo , las secuencias generalmente se conectan al terminal de texto en el que se ejecuta el shell, pero se pueden cambiar con una redirección o una canalización . De manera más general, un proceso hijo hereda los flujos estándar de su proceso padre .

Solicitud

Los flujos estándar para entrada, salida y error en una configuración predeterminada común

Los usuarios generalmente conocen los flujos estándar como canales de entrada y salida que manejan datos provenientes de un dispositivo de entrada o que escriben datos desde la aplicación. Los datos pueden ser texto con cualquier codificación o datos binarios . Cuando un programa se ejecuta como demonio , su flujo de errores estándar se redirige a un archivo de registro, generalmente con fines de análisis de errores.

Los flujos se pueden utilizar para encadenar aplicaciones, lo que significa que el flujo de salida de un programa se puede redirigir para que sea el flujo de entrada de otra aplicación. En muchos sistemas operativos, esto se expresa enumerando los nombres de las aplicaciones, separados por el carácter de barra vertical, por esta razón a menudo se le llama carácter de canalización . Un ejemplo bien conocido es el uso de una aplicación de paginación , como more , que proporciona al usuario control sobre la visualización del flujo de salida en la pantalla.

Fondo

En la mayoría de los sistemas operativos anteriores a Unix , los programas tenían que conectarse explícitamente a los dispositivos de entrada y salida apropiados. Las complejidades específicas del sistema operativo hicieron que esta fuera una tarea de programación tediosa. En muchos sistemas era necesario obtener control de la configuración del entorno, acceder a una tabla de archivos local, determinar el conjunto de datos deseado y manejar el hardware correctamente en el caso de un lector de tarjetas perforadas , una unidad de cinta magnética , una unidad de disco , una impresora de líneas , una perforadora de tarjetas. , o terminal interactivo.

Uno de los varios avances innovadores de Unix fueron los dispositivos abstractos , que eliminaron la necesidad de que un programa supiera o le importara con qué tipo de dispositivos se estaba comunicando [ cita requerida ] . Los sistemas operativos más antiguos imponían al programador una estructura de registros y, con frecuencia, una semántica de datos y un control de dispositivos no ortogonales . Unix eliminó esta complejidad con el concepto de flujo de datos: una secuencia ordenada de bytes de datos que se puede leer hasta el final del archivo . Un programa también puede escribir bytes según lo desee y no es necesario, y no puede declarar fácilmente su recuento o agrupación.

Otro avance de Unix fue asociar automáticamente la entrada y la salida al teclado y la pantalla del terminal, respectivamente, de forma predeterminada [ cita necesaria ] : el programa (y el programador) no hizo absolutamente nada para establecer la entrada y la salida para un programa típico de proceso de entrada y salida ( a menos que elija un paradigma diferente). Por el contrario, los sistemas operativos anteriores generalmente requerían algún lenguaje de control de trabajo (a menudo complejo ) para establecer conexiones, o la carga equivalente tenía que ser orquestada por el programa. [ cita necesaria ]

Dado que Unix proporcionaba flujos estándar, el entorno de ejecución de Unix C estaba obligado a soportarlo también. Como resultado, la mayoría de los entornos de ejecución de C (y los descendientes de C ), independientemente del sistema operativo, proporcionan una funcionalidad equivalente.

Entrada estándar (stdin)

La entrada estándar es una secuencia desde la cual un programa lee sus datos de entrada. El programa solicita transferencias de datos mediante el uso de la operación de lectura . No todos los programas requieren entrada de flujo. Por ejemplo, los programas dir y ls (que muestran los nombres de los archivos contenidos en un directorio) pueden tomar argumentos de línea de comandos , pero realizan sus operaciones sin ninguna entrada de datos de flujo.

A menos que se redirija , la entrada estándar se hereda del proceso principal. En el caso de un shell interactivo, generalmente está asociado con el dispositivo de entrada de un terminal (o pseudo terminal ) que en última instancia está vinculado al teclado de un usuario .

En los sistemas POSIX , el descriptor de archivo para la entrada estándar es 0 (cero); la definición POSIX es ; la abstracción de C correspondiente se proporciona a través de la variable global. De manera similar, la variable de tipo global de C++ proporciona una abstracción a través de flujos de C++ . Existen abstracciones similares en las bibliotecas de E/S estándar de prácticamente todos los lenguajes de programación .<unistd.h>STDIN_FILENO<stdio.h>FILE* stdinstd::cin<iostream>

Salida estándar (stdout)

La salida estándar es una secuencia en la que un programa escribe sus datos de salida. El programa solicita la transferencia de datos con la operación de escritura . No todos los programas generan resultados. Por ejemplo, el comando de cambio de nombre de archivo (también llamado mv , move o ren ) no dice nada sobre el éxito.

A menos que se redirija , la salida estándar se hereda del proceso principal. En el caso de un shell interactivo, suele ser el terminal de texto que inició el programa.

El descriptor de archivo para la salida estándar es 1 (uno); la definición POSIX es ; la variable C correspondiente es ; de manera similar, la variable C++ es .<unistd.h>STDOUT_FILENO<stdio.h>FILE* stdout<iostream>std::cout

Error estándar (stderr)

El error estándar es otro flujo de salida que suelen utilizar los programas para generar mensajes de error o diagnósticos. Es una transmisión independiente de la salida estándar y se puede redirigir por separado.

Esto resuelve el problema de semipredicado , permitiendo distinguir la salida y los errores, y es análogo a una función que devuelve un par de valores; consulte Problema de semipredicado: retorno con múltiples valores . El destino habitual es el terminal de texto que inició el programa para brindar la mejor oportunidad de ser visto incluso si se redirige la salida estándar (por lo que no se observa fácilmente). Por ejemplo, la salida de un programa en una canalización se redirige a la entrada del siguiente programa o a un archivo de texto, pero los errores de cada programa siguen yendo directamente al terminal de texto para que el usuario pueda revisarlos en tiempo real. [2]

Es aceptable y normal dirigir la salida estándar y el error estándar al mismo destino, como la terminal de texto. Los mensajes aparecen en el mismo orden en que el programa los escribe, a menos que se trate de almacenamiento en búfer . Por ejemplo, en situaciones comunes, el flujo de error estándar no tiene búfer, pero el flujo de salida estándar tiene búfer de línea; en este caso, el texto escrito en error estándar más tarde puede aparecer antes en el terminal, si el búfer de flujo de salida estándar aún no está lleno.

POSIX define el descriptor de archivo para el error estándar como 2 (dos); el archivo de encabezado <unistd.h> proporciona el símbolo ; [3] la variable C correspondiente es . El encabezado estándar de C++ proporciona dos variables asociadas con esta secuencia: y , la primera sin almacenamiento en búfer y la segunda usando el mismo mecanismo de almacenamiento en búfer que todas las demás secuencias de C++.STDERR_FILENO<stdio.h>FILE* stderr<iostream>std::cerrstd::clog

Los shells estilo Bourne permiten redirigir el error estándar al mismo destino al que se dirige la salida estándar.

2>&1

Los shells de estilo csh permiten redirigir el error estándar al mismo destino al que se dirige la salida estándar.

>&

El error estándar se agregó a Unix en la década de 1970 después de que varias ejecuciones de fotocomposición desperdiciadas terminaron con mensajes de error que se componían en lugar de mostrarse en la terminal del usuario. [4]

Línea de tiempo

Década de 1950: Fortran

Fortran tiene el equivalente a los descriptores de archivos de Unix: por convención, muchas implementaciones de Fortran usan números de unidad UNIT=5para stdin, UNIT=6stdout y UNIT=0stderr. En Fortran-2003, el ISO_FORTRAN_ENVmódulo intrínseco se estandarizó para incluir las constantes nombradas INPUT_UNIT, OUTPUT_UNITy ERROR_UNITpara especificar de forma portátil los números de unidad.

! Ejemplo de FORTRAN 77 PROGRAMA PRINCIPAL NÚMERO ENTERO LEER ( UNIDAD = 5 , * ) NÚMERO ESCRIBIR ( UNIDAD = 6 , '(A,I3)' ) ' EL NÚMERO ES: ' , FINAL DEL NÚMERO       
! Programa de ejemplo de Fortran 2003 uso principal iso_fortran_env implícito ninguno entero :: número leído ( unidad = INPUT_UNIT , * ) número escrito ( unidad = OUTPUT_UNIT , ' (a,i3)' ) 'El número es:' , número final del programa            

1960: ALGOL 60

ALGOL 60 fue criticado por no tener acceso estándar a archivos. [ cita necesaria ]

1968: ALGOL 68

Las instalaciones de entrada y salida de ALGOL 68 se denominaron colectivamente transput. [5] Koster coordinó la definición del estándar de transputación . El modelo incluía tres canales estándar: stand in, stand outy stand back.

Década de 1970: C y Unix

En el lenguaje de programación C , los flujos de entrada, salida y error estándar se adjuntan a los descriptores de archivos Unix existentes 0, 1 y 2 respectivamente. [6] En un entorno POSIX , se deben utilizar las definiciones < unistd.h > STDIN_FILENO , STDOUT_FILENO o STDERR_FILENO en lugar de números mágicos . También se proporcionan punteros de archivo stdin , stdout y stderr .

Ken Thompson (diseñador e implementador del sistema operativo Unix original) modificó la clasificación en la Versión 5 de Unix para aceptar "-" como representación de entrada estándar, que se extendió a otras utilidades y se convirtió en parte del sistema operativo como un archivo especial en la Versión 8 . Los diagnósticos fueron parte del resultado estándar hasta la Versión 6 , después de lo cual Dennis M. Ritchie creó el concepto de error estándar. [7]

1995: java

En Java , los flujos estándar se denominan System.in(para stdin), System.out(para stdout) y System.err(para stderr). [8]

public static void main ( String args [] ) { prueba { BufferedReader br = nuevo BufferedReader ( nuevo InputStreamReader ( System . in )); Cadena s = br . leerLínea (); número doble = Doble . parseDouble ( s ); Sistema . afuera . println ( "El número es:" + número ); } captura ( Excepción e ) { Sistema . errar . println ( "Error:" + e . getMessage ()); } }                                  

Década de 2000: .NET

En C# y otros lenguajes .NET , las secuencias estándar se denominan System.Console.In(para stdin), System.Console.Out(para stdout) y System.Console.Error(para stderr). [9] Las capacidades básicas de lectura y escritura para los flujos stdin y stdout también son accesibles directamente a través de la clase System.Console(por ejemplo, System.Console.WriteLine()se pueden usar en lugar de System.Console.Out.WriteLine()).

System.Console.In, System.Console.Outy System.Console.Errorson objetos System.IO.TextReader(stdin) y System.IO.TextWriter(stdout, stderr), que solo permiten el acceso a los flujos estándar subyacentes en forma de texto. El acceso binario completo a los flujos estándar se debe realizar a través de los System.IO.Streamobjetos devueltos por System.Console.OpenStandardInput()y System.Console.OpenStandardOutput()respectivamente System.Console.OpenStandardError().

// Ejemplo de C# public static int Main ( cadena [] args ) { prueba { cadena s = Sistema . Consola . En . Leerlínea (); número doble = doble . Analizar ( s ); Sistema . Consola . Afuera . WriteLine ( "El número es: {0:F3}" , número ); devolver 0 ;                   // Si Parse() arrojó una excepción } catch ( ArgumentNullException ) { System . Consola . Error . WriteLine ( "¡No se ingresó ningún número!" ); } captura ( FormatoException ) { Sistema . Consola . Error . WriteLine ( "¡El valor especificado no es un número válido!" ); } captura ( OverflowException ) { Sistema . Consola . Error . WriteLine ( "¡El número especificado es demasiado grande!" ); }                  retorno - 1 ; } 
' Ejemplo de Visual Basic .NETFunción pública principal () como número entero Pruebe Dim s como cadena = sistema . Consola . [ En ] . ReadLine () Número atenuado Como Doble = Doble . Sistema de análisis ( s ) . Consola . Afuera . WriteLine ( "El número es: {0:F3}" , número ) Devuelve 0                      ' Si Parse() arroja una excepción Catch ex As System . Sistema ArgumentNullException . Consola . [ Error ] . WriteLine ( "¡No se ingresó ningún número!" ) Captura ex2 como sistema . Sistema de excepción de formato . Consola . [ Error ] . WriteLine ( "¡El valor especificado no es un número válido!" ) Captura ex3 como sistema . Sistema de excepción de desbordamiento . Consola . [ Error ] . WriteLine ( "¡El número especificado es demasiado grande!" ) Fin del intento                  Retorno - 1 Función Final  

Al aplicar la System.Diagnostics.Process clase, se pueden usar las propiedades StandardInput de instancia , StandardOutputy StandardErrorde esa clase para acceder a los flujos estándar del proceso.

2000 -: Pitón (2 o 3)

El siguiente ejemplo, escrito en Python , muestra cómo redirigir la entrada estándar tanto a la salida estándar como a un archivo de texto.

#!/usr/bin/env pitón sistema de importación# Guarda la salida estándar actual para que podamos revertir sys.stdout# después de completar nuestra redirecciónstdin_fileno  =  sys . entrada estándarstdout_fileno  =  sys . salida estándar# Redirigir sys.stdout al archivosistema . salida estándar  =  abrir ( 'miarchivo.txt' ,  'w' )ctr  =  0para  entradas  en  stdin_fileno : ctrs  =  cadena ( ctr ) # Imprime en la salida estándar redirigida () sistema . salida estándar . escribe ( ctrs  +  ") esto es para el redirigido --->"  +  inps  +  ' \n ' ) # Imprime en el controlador de salida estándar guardado real stdout_fileno . escribir ( ctrs  +  ") esto es al real --->"  +  inps  +  ' \n ' ) ctr  =  ctr  +  1#Cerrar el archivosistema . salida estándar . cerca ()# Restaurar sys.stdout a nuestro antiguo administrador de archivos guardadossistema . salida estándar  =  salida_estándar_fileno

GUI

Las interfaces gráficas de usuario (GUI) no siempre utilizan los flujos estándar; lo hacen cuando las GUI son envoltorios de scripts subyacentes y/o programas de consola, por ejemplo, la GUI del administrador de paquetes Synaptic , que envuelve comandos apt en Debian y/o Ubuntu. Las GUI creadas con herramientas de secuencias de comandos como Zenity y KDialog por el proyecto KDE [10] utilizan stdin, stdout y stderr, y se basan en secuencias de comandos simples en lugar de una GUI completa programada y compilada en C/C++ usando Qt , GTK u otros. marco de widget propietario equivalente.

El menú Servicios , implementado en NeXTSTEP y Mac OS X , también es análogo a las transmisiones estándar. En estos sistemas operativos, las aplicaciones gráficas pueden proporcionar funcionalidad a través de un menú de todo el sistema que opera con la selección actual en la GUI, sin importar en qué aplicación.

Algunos programas GUI, principalmente en Unix, todavía escriben información de depuración en el error estándar. Otros (como muchos reproductores multimedia Unix) pueden leer archivos desde la entrada estándar. Los programas populares de Windows que abren una ventana de consola separada además de sus ventanas GUI son los emuladores pSX y DOSBox .

El servidor GTK puede utilizar stdin como interfaz de comunicación con un programa interpretado para realizar una GUI.

El paradigma Common Lisp Interface Manager "presenta" elementos GUI enviados a un flujo de salida extendido.

Ver también

Referencias

  1. ^ DM Ritchie, "Un sistema de entrada-salida de flujo", Revista técnica de AT&T Bell Laboratories, 68 (8), octubre de 1984.
  2. ^ "¿Qué son stdin, stdout y stderr en Linux? | CodePre.com". 2 de diciembre de 2021 . Consultado el 8 de abril de 2022 .
  3. ^ "<unistd.h>". Especificaciones básicas de Open Group, edición 6: IEEE Std 1003.1, edición 2004 . El grupo abierto. 2004.
  4. ^ Johnson, Steve (11 de diciembre de 2013). "[TUHS] Fotocomponedora Graphic Systems C/A/T" (Lista de correo). Archivado desde el original el 25 de septiembre de 2020 . Consultado el 7 de noviembre de 2020 .
  5. ^ "Informe revisado sobre el lenguaje algorítmico Algol 68", editado por A. van Wijngaarden, BJ Mailloux, JEL Peck, CHA Koster, M. Sintzoff, CH Lindsey, LGLT Meertens y RG Fisker, Sección 10.3.
  6. ^ "Stdin(3): flujos de E/S estándar: página de manual de Linux". die.net . Archivado desde el original el 8 de junio de 2023.
  7. ^ McIlroy, Doctor en Medicina (1987). Un lector de Research Unix: extractos comentados del Manual del programador, 1971-1986 (PDF) (Informe técnico). CSTR. Laboratorios Bell. 139. Archivado (PDF) desde el original el 15 de diciembre de 2023.
  8. ^ "Sistema (Plataforma Java SE 7)". Centro de ayuda de Oracle . Consultado el 20 de julio de 2012 .
  9. ^ ".NET Framework 4.7.1, mscorlib, console.cs". Fuente de referencia: Microsoft . Archivado desde el original el 10 de diciembre de 2017 . Consultado el 10 de diciembre de 2017 .
  10. ^ Kissling, Kristian (2009). "Añadiendo elementos gráficos a tus scripts con Zenity y KDialog". Revista Linux . Consultado el 11 de abril de 2021 .

Fuentes

enlaces externos