java - try - Probar con recursos al llamar a super constructor
try with resources jdbc (3)
¿Hay alguna buena manera de usar try-with-resources al abrir un InputStream
en un constructor y luego pasárselo a un super constructor?
Básicamente lo que quiero hacer es esto:
public class A {
public A(InputStream stream) {
// Do something with the stream but don''t close it since we didn''t open it
}
}
public class B {
public B(File file) {
// We open the stream so we need to ensure it''s properly closed
try (FileInputStream stream = new FileInputStream(file)) {
super(new FileInputStream(file));
}
}
}
Pero, por supuesto, ya que super
debe ser la primera declaración en el constructor, esto no está permitido. ¿Hay alguna buena manera de lograr esto?
Considere usar un método de fábrica estático en lugar de usar el constructor directamente. Haga que al menos el constructor de B
privado, y cree un método como
private B(InputStream is) {
super(is);
// Whatever else is needed
}
public static B newInstance(File file) {
B result;
try (FileInputStream stream = new FileInputStream(file)) {
result = new B(stream);
}
// Further processing
return result;
}
Lamentablemente no tengo un compilador a mano para probar, pero no podrías hacer lo siguiente.
public class B {
private static InputStream file2stream(File f){
// We open the stream so we need to ensure it''s properly closed
try (FileInputStream stream = new FileInputStream(file)) {
return stream;
}catch(/*what you need to catch*/){
//cleanup
// possibly throw runtime exception
}
}
public B(File file) {
super(file2stream(file))
}
}
Otra forma de ir:
public class A {
protected A(){
// so he can''t be called from the outside, subclass ensure that init is done properly.
}
public A(InputStream stream) {
init(stream);
}
// not be able to call it from outside
protected final init(InputStream is){
//here goes the code
}
}
public class B {
public B(File file) {
// We open the stream so we need to ensure it''s properly closed
try (FileInputStream stream = new FileInputStream(file)) {
init(stream);
}
}
}
Estoy publicando esto aquí como una posible respuesta, sin embargo aquí considero:
- Puede actualizar el código de A
- Está moviendo el código del constructor a un método de inicio, gracias al constructor de argumento vacío protegido, solo las subclases tienen que manejar la llamada para iniciar correctamente. Algunos pueden ver que no está tan bien diseñado. Mi punto es que tan pronto como subcompones algo, debes saber más sobre eso que cuando lo usas.