Je cherchais un moyen de résoudre ce problème. Lisez toutes les réponses précédentes mais aucune ne m'a aidé. S'agit-il d'une erreur avec SonarQube?
public class Br { public String loader(String FilePath){ BufferedReader br; String str = null; StringBuilder strb = new StringBuilder(); try { br = new BufferedReader(new FileReader(FilePath)); while ((str = br.readLine()) != null) { strb.append(str).append("\n"); } } catch (FileNotFoundException f){ System.out.println(FilePath+" does not exist"); return null; } catch (IOException e) { e.printStackTrace(); } return strb.toString(); } }
3 Réponses :
Le code que vous avez écrit fuit en effet des ressources car vous ne fermez pas votre BufferedReader. L'extrait suivant devrait faire l'affaire:
public String loader(String filePath){ String str = null; StringBuilder strb = new StringBuilder(); // try-with-resources construct here which will automatically handle the close for you try (FileReader fileReader = new FileReader(filePath); BufferedReader br = new BufferedReader(fileReader);){ while ((str = br.readLine()) != null) { strb.append(str).append("\n"); } } catch (FileNotFoundException f){ System.out.println(filePath+" does not exist"); return null; } catch (IOException e) { e.printStackTrace(); } return strb.toString(); }
Si vous rencontrez toujours des problèmes avec ce code, alors oui, c'est la faute de SonarQubes :-)
Oh ok alors c'est une erreur SonarQubes! J'ai essayé cela avant, j'ai essayé à nouveau maintenant et j'ai toujours eu la même erreur.Merci!
Peut-être un long plan, mais peut-être que SonarQube nécessite que FileReader et BufferedReader soient déclarés séparément dans la construction try-with-resources? Ajusté mon échantillon en fonction de cela.
Il semble que vous vouliez simplement lire toutes les lignes d'un fichier. Vous pouvez utiliser ceci:
public String loader(String FilePath) { try(Scanner s = new Scanner(new File(FilePath).useDelimiter("\\A")) { return s.hasNext() ? s.next() : null; } catch(IOException e) { throw new UncheckedIOException(e); } }
Vous n'appelez pas br.close ()
ce qui signifie risquer une fuite de ressources. Afin de fermer de manière fiable le BufferedReader
, vous avez deux options:
en utilisant un bloc enfin
:
public String loader(String FilePath) { String str = null; StringBuilder strb = new StringBuilder(); // the following line means the try block takes care of closing the resource try (BufferedReader br = new BufferedReader(new FileReader(FilePath))) { while ((str = br.readLine()) != null) { strb.append(str).append("\n"); } } catch (FileNotFoundException f) { System.out.println(FilePath + " does not exist"); return null; } catch (IOException e) { e.printStackTrace(); } return strb.toString(); }
en utilisant une instruction try
-with-resources:
public String loader(String FilePath) { // initialize the reader with null BufferedReader br = null; String str = null; StringBuilder strb = new StringBuilder(); try { // really initialize it inside the try block br = new BufferedReader(new FileReader(FilePath)); while ((str = br.readLine()) != null) { strb.append(str).append("\n"); } } catch (FileNotFoundException f) { System.out.println(FilePath + " does not exist"); return null; } catch (IOException e) { e.printStackTrace(); } finally { // this block will be executed in every case, success or caught exception if (br != null) { // again, a resource is involved, so try-catch another time try { br.close(); } catch (IOException e) { e.printStackTrace(); } } } return strb.toString(); }
Ok, donc la méthode avec enfin les crochets a très bien fonctionné! Je ne sais pas pourquoi essayer avec des ressources n'a pas fonctionné! Merci beaucoup!
@Lol De rien! C'est la version classique. Avez-vous essayé l'autre? SonarQube s'en est-il plaint? Pensez à accepter la réponse si cela vous a aidé, cela vous donnerait aussi un peu de réputation.
La deuxième version ne semble pas fonctionner pour moi! Donnerait la même erreur qu'avant.
@Lol C'est intéressant ... N'est-ce pas SonarQube lui-même qui a déclaré Utiliser try-with-resources ou fermer ce "BufferedReader" dans une clause "finally" ? Le titre de votre question est un message d'erreur, n'est-ce pas?
Oui c'était! Lorsque j'ai essayé d'essayer avec des ressources, je me suis retrouvé dans la même déclaration, ce qui est totalement étrange.
@Lol qui pourrait être un problème déjà connu de SonarQube ... Ce n'est pas de notre faute ;-)
Salut, j'ai ajouté try-with-resource à mon code et j'ai obtenu l'erreur «StatementIsClosedException: Aucune opération autorisée après la fermeture de l'instruction», que dois-je faire avec cela?
@Cecilia Vous ne pouvez pas accéder à la ressource en dehors de la portée du bloc try
-with-resources, mais vous le faites évidemment, ce qui conduit à cette Exception
. Stockez les données dont vous avez besoin dans des structures de données définies en dehors de cette portée.
Exécutez votre code 1 million de fois. Vous verrez que vous avez créé une fuite de ressources. Vous ouvrez des ressources, mais ne les fermez jamais
Il vous manque la méthode
br.close ()
pour éviter une fuite de ressources. Ceci peut être réalisé dans un blocfinally
après les blocscatch
ou dans untry (BufferedReader br = new BufferedReader (new FileReader (FilePath))) {.. ..
J'ai essayé ce que vous avez dit, mais a fini par être une erreur.
Utilisez toujours par défaut try-with-resources.
Ça n'aiderait pas du tout. J'ai essayé tout ce qui a été suggéré a encore beaucoup d'autres erreurs. Si j'essaye d'ajouter finalement {}, j'obtiens "br n'a pas été initialisé". Après avoir défini br sur null, je me retrouve dans d'autres erreurs et ainsi de suite.
Je suis bizarre que vous ayez
return null
dans la première exception, même si votrereturn strb.toString ()
est en dehors detry
, et leIOException
n'a pas de valeur nulle de retour. Soit mettezreturn null
dans les deux exceptions avec lereturn strb.toString ()
dans le try, soit laissez-le à l'extérieur sans lesreturn null
s. Cela rend simplement votre code déroutant car dans IOException, vous retournerez strb.toString (). (Ce n'est pas vraiment lié à votre autre problème cependant)