studio programacion para móviles libros libro edición desarrollo curso aplicaciones scala scala-2.8

scala - para - manual de programacion android pdf



Paquete de objetos (3)

¿Qué son los objetos del paquete, no tanto el concepto sino su uso?

Intenté que funcionara un ejemplo y la única forma de trabajar fue la siguiente:

package object investigations { val PackageObjectVal = "A package object val" } package investigations { object PackageObjectTest { def main(args: Array[String]) { println("Referencing a package object val: " + PackageObjectVal) } } }

Las observaciones que he hecho hasta ahora son:

package object _root_ { ... }

está prohibido (lo cual es razonable),

package object x.y { ... }

también está prohibido.

Parece que un objeto paquete debe declararse en el paquete principal inmediato y, si se escribe como se indica anteriormente, se requiere el formulario de declaración del paquete delimitado por soporte.

¿Son de uso común? ¿Si es así, cómo?


Normalmente pondrías tu objeto de paquete en un archivo separado llamado package.scala en el paquete al que corresponde. También puede usar la sintaxis del paquete anidado, pero eso es bastante inusual.

El caso de uso principal para los objetos de paquete es cuando necesita definiciones en varios lugares dentro de su paquete, así como también fuera del paquete cuando usa la API definida por el paquete. Aquí hay un ejemplo:

// file: foo/bar/package.scala package foo package object bar { // package wide constants: def BarVersionString = "1.0" // or type aliases type StringMap[+T] = Map[String,T] // can be used to emulate a package wide import // especially useful when wrapping a Java API type DateTime = org.joda.time.DateTime type JList[T] = java.util.List[T] // Define implicits needed to effectively use your API: implicit def a2b(a: A): B = // ... }

Ahora las definiciones dentro de ese objeto de paquete están disponibles dentro de todo el paquete foo.bar . Además, las definiciones se importan cuando alguien ajeno a ese paquete importa foo.bar._ .

De esta forma, puede evitar que el cliente API emita importaciones adicionales para usar su biblioteca de manera efectiva, por ejemplo, en scala-swing necesita escribir

import swing._ import Swing._

tener todas las bondades como onEDT y conversiones implícitas de Tuple2 a Dimension .



Si bien la respuesta de Moritz es acertada, una cosa adicional a tener en cuenta es que los objetos del paquete son objetos. Entre otras cosas, esto significa que puedes crearlos a partir de los rasgos, usando la herencia mix-in. El ejemplo de Moritz podría escribirse como

package object bar extends Versioning with JodaAliases with JavaAliases { // package wide constants: override val version = "1.0" // or type aliases type StringMap[+T] = Map[String,T] // Define implicits needed to effectively use your API: implicit def a2b(a: A): B = // ... }

Aquí, versionar es un rasgo abstracto, que dice que el objeto del paquete debe tener un método de "versión", mientras que las alias JodaAliases y Java son rasgos concretos que contienen alias de tipo práctico. Todos estos rasgos pueden ser reutilizados por muchos objetos de paquete diferentes.