¿Cuándo entran en uso las 'funciones estáticas'?

25

Bien, he aprendido qué es una función estática, pero todavía no veo por qué son más útiles que las funciones de miembros privados. Esto podría ser una especie de pregunta nueva aquí, pero ¿por qué no simplemente reemplazar todas las funciones de miembros privados con funciones estáticas?

Templario oscuro
fuente
1
¿No debería ser eso "reemplazar todas las funciones estáticas con funciones de miembros privados"? Actualmente, estás afirmando que no ves el punto de los métodos estáticos y continúas preguntándote por qué no usamos más de ellos.
55
¿Qué es una "función estática"? En C ++, hay al menos dos significados (y la última vez que miré los borradores de C ++ 11, eliminaron el aviso de desaprobación staticpor limitar las funciones al alcance del archivo.
David Thornley
¿Se refiere a "función estática" en el sentido de función libre de estática de alcance de archivo en C / C ++, o como "función / método estático de memenber"? ¡Es una gran diferencia!
Jan Hudec
@ JanHudec: Creo que dada la presencia de private membernosotros podemos asumir con seguridad que el OP está preguntando sobre el concepto OO y no tiene idea sobre la estática del alcance del archivo.
Matthieu M.
@MatthieuM .: En realidad, la presencia de 'miembro privado' es exactamente lo que me lleva a creer que se refiere a funciones estáticas en el sentido de C ++. Debido a que las funciones estáticas de ámbito de archivo y las funciones de miembros privados son las dos cosas que tienen un uso muy similar en C ++, mientras que reemplazar un miembro estático público por un miembro privado no estático simplemente no tiene mucho sentido. Lamentablemente, OP no parece estar respondiendo.
Jan Hudec

Respuestas:

25

Suponiendo que está usando OOP , use funciones estáticas cuando no dependen de ningún miembro de la clase. Todavía pueden ser privados, pero de esta manera están optimizados ya que no dependen de ninguna instancia del objeto relacionado.

Aparte de lo anterior, encuentro útiles las funciones estáticas cuando no desea crear una instancia de un objeto solo para ejecutar una función pública en él. Este es principalmente el caso de las clases auxiliares que contienen funciones públicas para realizar un trabajo repetitivo y general, pero no necesitan mantener ningún estado entre llamadas.

Bernardo
fuente
Gracias Bernard Por cierto, ¿sabes lo que significa para un compilador "vincular un método a la clase"?
Dark Templar
@Dark Templar: No puedo decir que lo haga. ¿Es esto específico de un idioma en particular?
Bernard
Tengo un pequeño problema con su definición "no dependen de ningún miembro de la clase". Las funciones estáticas de los miembros no pueden acceder a ningún miembro no estático, sin embargo, pueden acceder a los miembros estáticos. Los miembros estáticos son miembros de la clase.
newprint
@newprint: Tienes razón, sin embargo, eso no es lo que dije. Dije cuando no dependen de ningún miembro de la clase. Usar miembros estáticos está bien si son necesarios, pero puede que no siempre sea así.
Bernard
8

Tratando de obtener una explicación más simplificada que la anterior (muy buenas).

Un objeto es código + datos normalmente. Se utiliza un método estático cuando solo tiene que lidiar con la parte del "código" (no se mantienen datos / estados (excepto los miembros de datos estáticos)).

Brian Knoblauch
fuente
5

Porque no requieren una instancia y pueden ser públicos. Digamos que necesita una función para obtener el máximo común denominador (MCD; muy útil para clases de fracción; y sí, este es solo un ejemplo simple). No tiene sentido crear una clase de objetos cuyo único propósito es que pueda tener un thispuntero que no necesita ni utiliza gcd. Entonces usa un método estático para él, idealmente en la clase que realmente usa el MCD (por ejemplo, en la clase de fracción).

De hecho, si solo hay métodos estáticos, está haciendo mal la POO y debería cambiar a hacer POO en realidad o usar un lenguaje más apropiado para su paradigma.

usuario7043
fuente
¿No sería mejor en su ejemplo utilizar una función libre?
Ela782
2
@ Ela782 Si el lenguaje tiene funciones libres, sí.
Bien, gracias por la tranquilidad. Solo aprendí esta mejor práctica recientemente. Sin embargo, en este momento tengo problemas para ver cuándo una función miembro estática pública podría ser útil, digamos en un lenguaje como C ++. El caso de uso para ambos es cuando la función no depende o necesita una instancia de la clase, y luego, las funciones libres son la recomendación. Tal vez esta debería ser una nueva pregunta.
Ela782
1
@ Ela782 Sí, podría ser una buena pregunta. Dos puntos rápidos: específicamente en C ++, los miembros estáticos son útiles para la meta programación de plantillas, ya que puede pasar un tipo como parámetro de plantilla pero no un espacio de nombres. En general, las funciones estáticas se pueden usar para indicar que la función realmente pertenece a alguna clase, en lugar de pertenecer a un espacio de nombres (think stuff::Thing::Load(...)vs stuff::LoadThing()).
2

Los uso como funciones auxiliares para tareas comunes, por ejemplo:

  • Convertir grados en radianes (y viceversa);
  • Hashing una cuerda;
  • Convirtiendo de una enumeración a otra cosa (en este proyecto estoy trabajando, actúan como una tabla hash);

La mayoría de mis archivos que agrupan funciones estáticas tienen el sufijo Helper, lo que significa que es lo que hacen, me ayudan a llegar a algún lugar más rápido.

George Silva
fuente
2

En cuanto a qué es un método estático:

Los métodos estáticos no requieren una instancia de la clase ni pueden acceder implícitamente a los datos (o esto, self, Me, etc.) de dicha instancia. [ 1 ]

Ejemplos de cuándo son útiles los métodos estáticos:

  • Métodos globales / auxiliares
  • Obtener resultados de consultas de una clase de modelo de datos (llamar a un SP)

Solo úselos donde sea apropiado solamente.

  1. Si te encuentras copiando los mismos métodos en varios objetos, considera hacer que el método sea estático para que puedas seguir DRY.
  2. Use métodos estáticos si no necesita una instancia de un objeto (no está trabajando en las variables de instancia del objeto)

Si muchos de sus datos están fuera de los objetos y se están trabajando a través de métodos estáticos, entonces su código no está orientado a objetos y puede ser difícil de mantener.

descifrador
fuente
1

De hecho, estático y privado son ortogonales: un método puede ser estático o privado, o ninguno, o ambos.

Estático frente a no estático (también conocido como 'métodos de instancia') indica si el método funciona en la propia clase (estático) o en una instancia particular (no estático). Dependiendo del idioma, puede llamar a un método estático a través de una instancia, pero nunca puede acceder a la instancia a través de un método estático (lo que también implica que no puede llamar a ningún método no estático desde dentro de un método estático, simplemente porque no tiene , y desea implementar la suma; su método de suma podría llamarse como , pero probablemente tenga más sentido.this objeto). Utilice métodos estáticos para implementar comportamientos que estén conceptualmente vinculados a la clase, pero que no se 'unan' a una instancia en particular. Otro escenario en el que es posible que desee utilizar métodos estáticos es cuando tiene una función que opera en dos instancias de una clase, y ninguno de los operandos merece un estado privilegiado, por ejemplo, suponiendo que tiene una claseVectora.Add(b)Vector.Add(a, b)

Privado versus público son acerca de la visibilidad del método. Solo se puede acceder a los métodos privados desde el ámbito propio de la clase, mientras que los métodos públicos son accesibles desde cualquier lugar. El uso más importante para esto es la encapsulación: al hacer públicos solo los métodos y propiedades que son absolutamente necesarios para que el resto del código se comunique con su clase, limita los puntos en los que el código externo puede introducir problemas y evita problemas internos su clase de sangrar en el resto del proyecto.

Entonces, regla general:

  • Hacer que todas las funciones de los miembros sean privadas, excepto aquellas que deben llamarse desde fuera de la clase
  • hacer que todos los métodos sean métodos de instancia, a menos que tengan sentido incluso cuando no exista una instancia de la clase
tdammers
fuente
0

Utilizo métodos estáticos en C ++ y C # para las clases de utilidad, clases que no tienen datos de instancia, solo una forma de agrupar una colección de métodos útiles y relacionados.

int count1 = DBUtil::GetCountOfSlackerEmployees();
int count2 = DBUtil::GetCountOfEmployedSlackers();
Chris O
fuente
0

Suponiendo que está hablando de C ++ (no dijo) y tiene los términos correctos (es decir, no significa funciones / métodos de miembros):

Incluso una función de miembro privado todavía tiene que declararse en el encabezado, lo que significa que en realidad se convierte en parte de la API y ABI de la clase, a pesar de que el usuario no puede llamarla. Si agrega, modifica o elimina la función de miembro privado, está forzando la compilación de todas las clases dependientes (el encabezado ha cambiado, no se puede saber mejor) y cuando lo hace en una biblioteca, debe considerar la compatibilidad para la aplicación usando eso.

Por otro lado, las funciones estáticas con ámbito de archivo no obtienen un símbolo público, por lo que puede agregarlas, modificarlas o eliminarlas como desee y nada más allá de la unidad de compilación se verá afectada.

Jan Hudec
fuente
0

Por lo general, necesita un main estático para actuar como un punto de entrada para su programa. Eso podría ser algo importante.

Wyatt Barnett
fuente
0

Una función estática (y hay diferentes significados para ese término en diferentes idiomas) no requiere ningún estado retenido entre llamadas. Si está conceptualmente estrechamente relacionado con lo que hace una clase, conviértalo en una función de clase (como en una clase, no en un objeto), o si no, conviértalo en una función global (o nivel de módulo, lo que sea). No pertenece a un objeto si no necesita el estado del objeto.

Si le está pasando estado todo el tiempo, no es realmente una función sin estado, solo está haciendo una función con estado con sintaxis sin estado. En ese caso, probablemente pertenece al objeto que llama, o tal vez se indique una refactorización para alinear mejor el estado y el comportamiento.

kylben
fuente
0

"¿Por qué no simplemente reemplazar todas las funciones de miembros privados con funciones estáticas en su lugar?"

... porque un miembro privado puede acceder a los datos de la instancia mientras solo permite que ocurra a partir de llamadas realizadas dentro de otras funciones del miembro. La función estática puede ser privada, pero no podrá alterar o referirse a una instancia de la clase a menos que la instancia se pase como un parámetro.

jheriko
fuente
0

Es curioso cómo nadie ha podido dar una buena respuesta todavía. No estoy seguro de que este sea tampoco. Probablemente deberías tomar como una pista de que deberían usarse lo menos posible. Después de todo, son procesales en lugar de OOP.

Aquí hay algunos ejemplos más:

En Obj-C, donde se llaman métodos de clase, se usan comúnmente como envoltorios de asignación donde el objeto se coloca en el grupo de conteo de referencia antes de ser devuelto.

Otro ejemplo de Obj-C es registrar una nueva clase en una colección de clases. Digamos que tiene un conjunto de clases, cada una de las cuales maneja un tipo de archivo. Cuando crea una nueva clase para un nuevo tipo de archivo, puede registrarlo en la colección (una variable global) utilizando un método estático en la clase que determina el tipo de archivo.

En C ++, otro uso que se me ocurre es detectar suavemente los errores. Su función de constructor no puede fallar, excepto lanzando una excepción. Puede establecer una variable de instancia de error, pero eso no siempre es apropiado. En su lugar, puede hacer las partes que pueden fallar en un contenedor estático y luego asignar y devolver el nuevo objeto, o NULL en caso de falla.

Por Johansson
fuente
0

Digamos que quieres calcular el seno de algo.

Sin estática:

Math math = new Math()
double y = math.sin(x)

Con estática:

double y = Math.sin(x)

No tiene sentido hacer sinno estático. No tiene estado y solo procesa la entrada.

Las funciones estáticas no están vinculadas a objetos particulares. Son funciones "generales" que son independientes del estado interno del objeto.

dagnelies
fuente
Los métodos estáticos no están "garantizados como apátridas". Si bien es cierto que no pueden usar datos de instancia, también tienen acceso a algún estado (es decir, miembros estáticos, tanto de la clase a la que pertenece el método estático como a otro estado visible globalmente, como las variables estáticas de otras clases).
@delnan: cierto ... tienes razón. Déjame corregir esto ahora mismo.
Dagnelies
Sin estática: x.sin(). Su respuesta supone que el pecado debería ser una función de "Matemáticas", mientras que claramente está operando en un doble.
AjahnCharles
0

Más tarde aquí, pero me gustaría intentar crear una definición precisa: las funciones estáticas son funciones que no hacen referencia o no pueden hacer referencia a propiedades / métodos de instancia de la clase que lo contiene.

En algunos lenguajes, como C #, puede haber campos o propiedades estáticos en las clases estáticas, por lo que no es exactamente correcto decir que no se usan para el estado; una función estática podría hacer uso del estado estático (global).

Básicamente, se reduce a: las funciones estáticas, como cualquier cosa estática, son útiles cuando tiene sentido que siempre estén disponibles sin depender de instancias no estáticas.

Las funciones auxiliares, como las funciones matemáticas, son un ejemplo frecuente, pero hay otras.

Si la clase que crea requiere que los datos sean inmutables, podría tener sentido crear funciones estáticas que tomen una instancia y pasen una nueva instancia ya que la instancia no puede (o no debe) cambiarse. Las clases de cadena, por ejemplo, pueden tener funciones estáticas que toman una cadena (o 2 o más) y devuelven una nueva cadena.

Otra razón podría ser que hay una clase que mantiene un estado global o datos de algún tipo. Puede haber funciones estáticas que funcionen con las propiedades estáticas o los campos en esa clase estática.

Mover
fuente
0

Me gustaría señalar otro uso de static f ().

http://www.parashift.com/c++-faq/named-ctor-idiom.html

Se reduce a esto: las staticfunciones le permiten crear "Constructores con nombre", es decir, nombra su función estática con un nombre adecuado y autodocumentado, y esta función estática llama a uno de los constructores (ya que los constructores tienen nombres idénticos y puede tener muchos de ellos, se hace difícil distinguir entre ellos).

nueva impresión
fuente