[BASE DE DONNEES MULTIMEDIA]



Documents pareils
Programmation d application Bases de données avec Java

OpenPaaS Le réseau social d'entreprise

Quelques patterns pour la persistance des objets avec DAO DAO. Principe de base. Utilité des DTOs. Le modèle de conception DTO (Data Transfer Object)

Java DataBaseConnectivity

COMMANDES SQL... 2 COMMANDES DE DEFINITION DE DONNEES... 2

Premiers Pas en Programmation Objet : les Classes et les Objets

Bases de Données relationnelles et leurs systèmes de Gestion

Programmer en JAVA. par Tama

Compte-rendu de projet de Système de gestion de base de données

TP Programmation Java / JDBC / Oracle

Paginer les données côté serveur, mettre en cache côté client

Application BdD et JDBC. Introduction 1/28. I Dans tout les cas, une seule problématique. I Quelques alternatives :

Introduction à JDBC. Accès aux bases de données en Java

Encryptions, compression et partitionnement des données

Licence de MIDO - 3ème année Spécialités Informatique et Mathématiques Appliquées

Bases de données relationnelles

Olivier Mondet

Les BASES de DONNEES dans WampServer

Bases de données Oracle Virtual Private Database (VPD) pour la gestion des utilisateurs d applications

TP Contraintes - Triggers

Cours Bases de données 2ème année IUT

A QUOI SERVENT LES BASES DE DONNÉES?

Module Administration BD Chapitre 1 : Surcouche procédurale dans les SGBDS

CREATION WEB DYNAMIQUE

Création et Gestion des tables

Langage SQL (1) 4 septembre IUT Orléans. Introduction Le langage SQL : données Le langage SQL : requêtes

Le langage SQL pour Oracle - partie 1 : SQL comme LDD

COURS WINDEV NUMERO 3

Utilisation de JAVA coté Application serveur couplé avec Oracle Forms Hafed Benteftifa Novembre 2008

Langage propre à Oracle basé sur ADA. Offre une extension procédurale à SQL

1. Base de données SQLite

TP n 2 Concepts de la programmation Objets Master 1 mention IL, semestre 2 Le type Abstrait Pile

A QUOI SERVENT LES BASES DE DONNÉES?

Le langage SQL Rappels

1. Qu'est-ce que SQL? La maintenance des bases de données Les manipulations des bases de données... 5

La persistance des données dans les applications : DAO, JPA, Hibernate... COMPIL 2010 francois.jannin@inp-toulouse.fr 1

PROJET 1 : BASE DE DONNÉES REPARTIES

Access et Org.Base : mêmes objectifs? Description du thème : Création de grilles d écran pour une école de conduite.

Java et les bases de données: JDBC: Java DataBase Connectivity SQLJ: Embedded SQL in Java. Michel Bonjour

PHP 5. La base de données MySql. A. Belaïd 1

NFA 008. Introduction à NoSQL et MongoDB 25/05/2013

Table des matières PRESENTATION DU LANGAGE DS2 ET DE SES APPLICATIONS. Introduction

Langage SQL : créer et interroger une base

Application web de gestion de comptes en banques

Accès aux bases de données

Les Triggers SQL. Didier DONSEZ. Université de Valenciennes Institut des Sciences et Techniques de Valenciennes

Corrigés détaillés des exercices

I4 : Bases de Données

TP1 : Initiation à Java et Eclipse

INTRODUCTION A JAVA. Fichier en langage machine Exécutable

Langage et Concepts de ProgrammationOrientée-Objet 1 / 40

ECR_DESCRIPTION CHAR(80), ECR_MONTANT NUMBER(10,2) NOT NULL, ECR_SENS CHAR(1) NOT NULL) ;

Modélisation PHP Orientée Objet pour les Projets Modèle MVC (Modèle Vue Contrôleur) Mini Framework

PHP et mysql. Code: php_mysql. Olivier Clavel - Daniel K. Schneider - Patrick Jermann - Vivian Synteta Version: 0.9 (modifié le 13/3/01 par VS)

Dossier I Découverte de Base d Open Office

Création d'un site dynamique en PHP avec Dreamweaver et MySQL

Gestion de base de données

Objectifs du TP : Initiation à Access

Licence Bio Informatique Année Premiers pas. Exercice 1 Hello World parce qu il faut bien commencer par quelque chose...

Le Langage SQL version Oracle

Construire des plug-ins pour SAS Management Console SAS 9.1

Stockage du fichier dans une table mysql:

Partie I : Créer la base de données. Année universitaire 2008/2009 Master 1 SIIO Projet Introduction au Décisionnel, Oracle

TP3 : Creation de tables 1 seance

LES TOUT PREMIERS PAS

Formation. Module WEB 4.1. Support de cours

Chapitre 10. Les interfaces Comparable et Comparator 1

Information utiles. webpage : Google+ : digiusto/

Procédures Stockées WAVESOFT ws_sp_getidtable Exemple : ws_sp_getnextsouche Exemple :... 12

Compétences Business Objects

Manuel d utilisation 26 juin Tâche à effectuer : écrire un algorithme 2

Cette application développée en C# va récupérer un certain nombre d informations en ligne fournies par la ville de Paris :

Plan du cours. Historique du langage Nouveautés de Java 7

BIRT (Business Intelligence and Reporting Tools)

les Formulaires / Sous-Formulaires Présentation Créer un formulaire à partir d une table...3

SQL Historique

TD3: tableaux avancées, première classe et chaînes

NF26 Data warehouse et Outils Décisionnels Printemps 2010

ISC Système d Information Architecture et Administration d un SGBD Compléments SQL

Bases de données - Modèle relationnel

Le Langage De Description De Données(LDD)

SUPPORT DE COURS / PHP PARTIE 3

Sage 100 CRM Guide de l Import Plus avec Talend Version 8. Mise à jour : 2015 version 8

PHP 4 PARTIE : BASE DE DONNEES

.NET - Classe de Log

Création d un service web avec NetBeans 5.5 et SJAS 9

Java Licence Professionnelle Cours 7 : Classes et méthodes abstraites

DEVAKI NEXTOBJET PRESENTATION. Devaki Nextobjects est un projet sous license GNU/Public.

BULK SMS Envoi en masse d un message texte moyennant un téléphone mobile (GSM)

RAPPELS SUR LES METHODES HERITEES DE LA CLASSE RACINE Object ET LEUR SPECIALISATION (i.e. REDEFINITION)

BASES DE DONNEES TP POSTGRESQL

Utilitaires méconnus de StrataFrame

Page 1 sur 5 TP3. Thèmes du TP : l la classe Object. l Vector<T> l tutorial Interfaces. l Stack<T>

Sommaire. I.1 : Alimentation à partir d un fichier Access (.mdb)...2

Prénom : Matricule : Sigle et titre du cours Groupe Trimestre INF1101 Algorithmes et structures de données Tous H2004. Loc Jeudi 29/4/2004

Plateforme PAYZEN. Définition de Web-services

Transcription:

2011 RAPPORT DE BASE DE DONNEES MULTIMEDIA M me Nadine Cullot David MARTINS Sylvain LAMBERTVELLER [BASE DE DONNEES MULTIMEDIA] Ce document constitue notre rapport pour l unité d enseignement «BDM». Il synthétise tout le travail effectué lors de notre projet. Aussi bien au niveau technique qu analytique.

Table des matières I - Introduction... 2 Spécificité des bases de données multimédia.... 2 Répartition des taches... 2 II - Partie analytique... 3 Caractéristiques générales de l application.... 3 Notre base de données.... 3 Notre schéma navigationnel.... 4 Les différents types... 5 Notre base de données finale... 7 III Partie conception de l application... 7 Gestion de l affichage des différents modules... 8 Partie Administration... 9 Administration des genres... 9 Administration des photos... 13 Partie Utilisateur... 18 Recherche de film... 18 Recherche textuelle de photos... 20 Recherche d acteur et de genre... 21 Comparaison de deux images... 21 Similarité d image... 24 Intermedia Text... 24 Thesaurus... 27 IV Conclusion... 30 Améliorations... 30 Et si on recommençait?... 30 Conclusion générale... 30 ANNEXES... 31 ANNEXE A... 31 RAPPORT DE BASE DE DONNEES MULTIMEDIA I - Introduction 1

I - Introduction Ce document constitue notre rapport pour l unité d enseignement «Base de données multimédia». Celui-ci décrira, de façon précise, quelles ont été les demandes spécifiques de ce projet, comment nous sommes nous organisés, comment notre travail s est déroulé et enfin, quels ont été les problèmes rencontrés. A titre informatif, nous avons développé notre application sous Windows XP à l aide de l IDE (Environnement de développement intégré) NetBeans. Nous travaillons avec une base de données Oracle 10g Le but de ce projet était de concevoir une application en JAVA qui allait nous permettre de manipuler notre base de données multimédia, celle-ci devait permettre de rechercher des images dans notre base. Quant au choix de la base de données, celui-ci nous appartenait totalement. Spécificité des bases de données multimédia. Les bases de données relationnelles sur lesquelles nous avons pu travailler jusqu à présent nous permettait de stocker uniquement des chaînes de caractères. Au vue de l évolution des technologies (Capacité de stockage, bande passante, puissance des machines, Sites internet de plus en plus complets,...) le besoin de pouvoir stocker, organiser et manipuler des données multimédia (données sonores, vidéos, images,...) ne cessait de croitre, c est ainsi que les bases de données multimédia sont nées. Les bases de données multimédia s appuient le plus souvent sur des architectures de base de données existantes. Les plus utilisées étant le modèle objet et le modèle relationnel. Répartition des tâches Etant donné que nous étions deux à travailler sur ce projet, il a fallu déterminer exactement le rôle de chacun. Concernant l élaboration de la base de données, nous avons décidé de la concevoir ensemble pour qu on puisse chacun s exprimer sur le sujet. La conception de la base de données comprenait la création du diagramme de classe, création du schéma navigationnel, création des types, création de la base de données puis enfin création des classes JAVA. Concernant la partie programmation, nous avons décidé de repartir les taches de la façon suivant : David s occuperait de la partie administration, et Sylvain de la partie utilisateur. Bien évidemment, si l un d entre nous finissait sa partie avant l autre, celui-ci aurait aidé son camarade. RAPPORT DE BASE DE DONNEES MULTIMEDIA I - Introduction 2

II - Partie analytique Caractéristiques générales de l application. Notre application devait répondre à des critères assez précis. Elle devait être développée à l aide du langage de programmation JAVA et devait implémenter les fonctionnalités suivantes : - Gérer les informations descriptives et contextuelles d images dans notre base de données. - Avoir des méta-données sur les images disponibles (taille de l image, format,...) - Informations sur le contenu de notre image (par exemple, notre image représente une voiture,...) - Concevoir toute une partie administration qui permet l ajout, l édition et la suppression de contenu dans notre base. - Une partie dédiée à l utilisateur qui lui donnera le moyen d interroger notre base via différents critères (format de l image, comparaison via une image modèles tout en ayant la possibilité de pondérer les critères de comparaison (couleur, forme,...), contenu de l image,...) Gestion des objets multimédia : Gestion des objets multimédia Comparaison d'image Recherche textuelle ORDImage ORDAudio ORDVideo ORDImageSignature Module Intermédia Text Thesaurus de termes Notre base de données. Dans note cas, nous avons choisi de réaliser une base de données assez simple pour ne pas s encombrer avec tout un tas de relations. En effet le but du projet était de manipuler des objets multimédia, non pas de réaliser une base de données complexe. Nous avons quand même réussi à faire une base assez cohérente. Voici le diagramme UML de notre base de données, il comportera 4 classes : RAPPORT DE BASE DE DONNEES MULTIMEDIA II - Partie analytique 3

La plupart des méthodes étant assez explicites, nous n allons pas les décrire, cependant, quelquesunes peuvent paraitre un peu ambiguës. - getwithrestriction : retourne un ensemble d objet répondant à des critères passés en paramètres de la méthode - compareimages : Compare deux images, retourne un tableau de chaîne de caractère qui représente l évaluation du score. - intermediatext : retourne un ensemble d objet photo répondant aux critères de recherche. - listethesaurus : retourne un ensemble de photo en fonction de critères définis préalablement. - chargement : charge l image dans la base de données. - similaritéphoto : retourne un ensemble de photos qui sont similaire à une image modèle. On constate que la grande majorité de ces méthodes sont uniquement présentes dans la classe Photo. Cela s explique tout simplement par le fait que c est dans cette classe que nous allons gérer nos objets multimédia. Nous avons implémenté toutes ces classes en JAVA. Notre schéma navigationnel. RAPPORT DE BASE DE DONNEES MULTIMEDIA II - Partie analytique 4

Lors de la réalisation d un schéma navigationnel, le nombre de possibilité pour réaliser celuici est assez important. Il n y a pas de solution unique (Comme pour un diagramme de classe d ailleurs) et il faut adapter la solution retenue en fonction de nos besoins. Dans notre cas, nous avons mis en œuvre tous ce que nous avons vus en cours (tables imbriquées, pointeurs,...). Voici la solution retenue : Les différents types RAPPORT DE BASE DE DONNEES MULTIMEDIA II - Partie analytique 5

Suite à l élaboration de notre schéma navigationnel, nous avons créé les types suivants. Nous listerons uniquement les différents types crées, mais si vous souhaitez consulter le code complet des types, nous vous invitons à aller consulter notre annexe «ANNEXE A» Types représentant des collections (collections de références) photos_type films_type Types destinés a la création des tables genre_type film_type acteur_type photo_type filmacteur_type (pour la relation entre film et acteur) types références (pour les collections) photo_ref_type film_ref_type Nous avons également implémenté des méthodes dans les types crées. Les types concernés sont genre_type et acteur_type. Nous allons prendre l exemple de genre_type. Ce type contient les méthodes : - updategenre(nomg IN VARCHAR2) ; Pour mettre à jour le nom du genre - suppgenre() ; Supprimer le genre de la BD En revanche, pour pouvoir appeler ces méthodes, nous devons passer par des procédures PLSQL. Avant de passer à autre chose, intéressons-nous au type photo_type. C est dans ce type que nous avons nos objets multimédias. Voici sa description : photo_type numphoto : integer nom : varchar2(100) taille : integer format : varchar2(10) description : varchar2(200) mots_cles : varchar2(200) signature : ORDSYS.ORDSignature image : ORDSYS.ORDImage acteurp ref acteur_type filmp ref film_type Focalisons notre attention sur les attributs signature et image. Si vous n avez fait que de la base de données relationnelle ou objet, vous n avez jamais dû voir ce type d attribut. Effectivement, ces types ne sont utilisés que dans les bases de données multimédia. Un attribut ORDSignature va nous servir principalement pour la comparaison d images. La signature d une image peut être assimilée à l ADN humain. La signature contient toutes les RAPPORT DE BASE DE DONNEES MULTIMEDIA II - Partie analytique 6

informations propre à l image comme sa forme, sa texture, sa couleur,... selon chaque zone de l image. Un attribut ORDImage est ce qui contient l image. Cela sert à stocker notre image dans la base de données. Notre base de données finale Apres la création des types, des méthodes et des procédures PLSQL, nous avons pu finalement créer notre base de données. Voici la liste des tables présentes : III Partie conception de l application RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 7

Gestion de l affichage des différents modules Etant donné que notre application comporte plusieurs modules, nous ne pouvions pas afficher tous ces modules dans une seule fenêtre. Pour la gestion des fenêtres (composants graphique sous forme de JPanel) nous avons utilisé un CardLayout. Un CardLayout permet d avoir un ensemble de composant graphique tel que l un d entre eux soit seulement visible à un moment donné. A l initialisation de l application, nous créons notre CardLayout vide. Nous créons ensuite nos composants graphiques, à savoir nos JPanel. Une fois ceux-là créés nous les ajoutons à notre CardLayout. Pour afficher une composant graphique, nous utilisons la méthode show(component) ; Pour le switch entre les différents Jpanel cards = new JPanel(); cards.setlayout(new CardLayout()); cards.add(mainpanel,"mainpanel"); mainpanel cards.add(new Jpnl_GenreAdmin(),"AdminGenrePanel"); cards.add(new Jpnl_FilmAdmin(),"AdminFilmPanel"); cards.add(new Jpnl_FilmacteurAdmin(),"AdminFilmacteurPanel"); cards.add(new Jpnl_Acteur_Admin(),"AdminActeurPanel"); cards.add(new Jpnl_PhotoAdmin(),"AdminPhotoPanel"); cards.add(new Crechercheacteur(),"RechercheacteurPanel"); cards.add(new Crecherchefilm(),"RecherchefilmPanel"); cards.add(new Jpnl_Comparaison_photo(),"ComparaisonphotoPanel"); cards.add(new Jpnl_similarité_photo(),"SimilaritePhotoPanel"); cards.add(new Jpnl_intermediaText(),"intermediaTextPanel"); cards.add(new Crecherchephoto(),"RecherchephotoPanel"); cards.add(new Jpnl_Thesaurus(),"ThesaurusPanel"); this.getframe().add(cards, BorderLayout.CENTER); Pour changer de fenêtre, nous avons à notre disposition un menu qui nous propose les différents modules accessibles. A chaque clique sur un item du menu, nous appellerons donc notre méthode show. Voici le code lors du clique sur le menu Administration > Film private void jmenuitemfilmactionperformed(java.awt.event.actionevent evt) { Jpnl_FilmAdmin j = ((Jpnl_FilmAdmin)cards.getComponent(2)); j.updatepanel(); ((CardLayout)cards.getLayout()).show(this.cards,"AdminFilmPanel"); A ce stade de l application, nous avons un système de Switch entre nos différents JPanel. Notons que c est grâce à ce système que nous avons pu travailler chacun de notre coté sans nous marcher sur les pieds. RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 8

Partie Administration La partie administration allait nous permettre de gérer notre base de données. Nous pouvons donc opérer sur celle ci en ajoutant, modifiant ou supprimant des t-uples. La partie administration se voit doté de 4 modules : - Administration des genres - Administration des Films - Administration des Acteurs - Administration des Photos Pour ne pas polluer ce rapport avec des pages inutiles, nous traiterons uniquement le module d administration de photo et de genre. Pourquoi? Et bien parce que les modules pour le genre, films et acteurs étant très étroitement similaires, l intérêt d expliquer le détail de chacun est très limité. En revanche, le module photo est peut-être celui le plus intéressant dans la mesure où c est dans ce module que nous allons enregistrer une photo dans la base de données. Administration des genres Le module d administration des genres comporte un tableau (JTable) qui contient la liste des genres enregistrés dans notre base de données. A tout instant, l utilisateur peut cliquer sur l une des lignes de ce tableau, soit pour modifier son contenu, soit pour afficher ses informations ou encore pour supprimer celui-ci. De plus, le JPanel d administration des genres comporte des champs textes permettant l ajout et la modification de genre (Pour la modification, il faut tout d abord sélectionner un genre dans le tableau). Initialisation du JPanel Lorsque que l utilisateur souhaite afficher ce JPanel (qui fait donc partie du CardLayout), celui ci va initialiser ses différents attributs. Cela consiste à : - Mettre le tableau à vide. - Mettre tous les champs textes à vide Pour l initialisation du tableau, c est lors du clique sur l item du menu que celui ci sera mis a jour. public Jpnl_GenreAdmin() Voila le code permettant { de réaliser ces actions : initcomponents(); JPanel_ajoutModif.setBorder(BorderFactory.createTitledBorder("Modification")); jpanelajoutgenre.setborder(borderfactory.createtitledborder("ajouter")); entetetblgenre = new String[2]; entetetblgenre[0] = "Numéro"; entetetblgenre[1] = "Nom"; listeg RAPPORT = null; DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 9 lbl_info.settext("");

Et la méthode qui permet de mettre à jour notre tableau public void updatepanel(){ Récupération de tous les genres try{ listeg = Cgenre.getAll(); catch(sqlexception e){ System.out.print(e.getMessage()); return; On vide le tableau dtm_listegenre = new DefaultTableModel(null,enteteTblGenre); tbladmin_genre.setmodel(dtm_listegenre); for(cgenre g: listeg){ String[] values = new String[2]; values[0] = ""+g.numero; values[1] = g.nom; dtm_listegenre.addrow(values); btn_modifgenre.setenabled(false); btn_suppression.setenabled(false); lbl_numgenre.settext("- - -"); txt_nomgenre.settext(""); Ajout d un genre Pour ajouter un genre dans notre BDD, nous procédons de la manière suivante : - Récupération des informations saisies par l utilisateur - Instanciation d un nouvel objet Genre (Classe JAVA qui permet d interagir avec notre private void BDD) btn_ajoutergenreactionperformed(java.awt.event.actionevent evt) { if(txt_ajoutg.gettext().equals("")){ - Appel de la méthode enregistrer(). lbl_info.settext("veuillez renseigner le nom du genre"); else{- Mise à jour du tableau en ajoutant l objet enregistrer directement a la fin. Cgenre g = new Cgenre(0,txt_ajoutG.getText()); try{ enregistrement de notre Genre g.enregistrer(); mise a jour du tableau String[] values = new String[2]; values[0] = ""+g.numero; values[1] = g.nom; RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 10 dtm_listegenre.addrow(values); txt_ajoutg.settext(""); lbl_info.settext("ajout confirmé");

Intéressons nous maintenant au code de la méthode enregistrer() de notre classe JAVA Genre. Cette méthode va manipuler la base de données via un objet Connection. Pour préparer la requête à l envoi, on instancie un objet PreparedStatement. Pour l envoyer, nous utiliserons la méthode executeupdate(). Cette dernière méthode renvoie un booléen qui retourne true si tout s est bien passé. La requete envoyée est une banale requete INSERT INTO permet d'enregistrer un genre public boolean enregistrer() throws SQLException{ boolean resultat = false; Connection cnx = BDM_projetView.connect; this.numero = this.getnewid(); String newgenre="insert into genre values("+this.numero+",'"+nom+"',films_type())"; PreparedStatement st = cnx.preparestatement(newgenre); if(st.executeupdate()!= 1){ resultat=false; else{ resultat=true; System.out.println("ajout du film confirmée"); return resultat; Modification d un genre La procédure est un peu différente, car il faut que l utilisateur choisisse le genre à modifier dans le tableau. Une fois cliqué sur une ligne du tableau, on met à jour les champs texte, l utilisateur pourra dès lors modifier les champs texte et cliquer sur modifier quand il le souhaite. Instanciation de l objet lors du clique sur une ligne du tableau : private void tbladmin_genremouseclicked(java.awt.event.mouseevent evt) { on active la modification et la suppression btn_modifgenre.setenabled(true); btn_suppression.setenabled(true); RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 11 lbl_info.settext(""); int index = tbladmin_genre.getselectedrow();

Il ne nous reste plus qu a modifier l enregistrement dans la base de données. Tout cela se fait via le clique du bouton modifier. private void btn_modifgenreactionperformed(java.awt.event.actionevent evt) { int selection=tbladmin_genre.getselectedrow(); int numero=integer.parseint(tbladmin_genre.getvalueat(selection, 0).toString()); if(txt_nomgenre.gettext().equals("")){ lbl_info.settext("veuillez renseigner le nom du genre"); else{ Cgenre gmodf = new Cgenre(numero,txt_nomGenre.getText()); try{ gmodf.modifier(); updatepanel(); lbl_info.settext("modification confirmée"); catch(exception e){ e.printstacktrace(); lbl_info.settext("erreur lors de la modification"); Nous pouvons voir que nous utilisons une méthode modifier de la classe Genre. Voici sa définition : utilisation de la procedure pour modifier le genre public boolean modifier() throws SQLException{ boolean resultat = false; Connection cnx = BDM_projetView.connect; CallableStatement cstmt = cnx.preparecall("{call majgenre(?,?)"); cstmt.setint(1, this.numero); cstmt.setstring(2, this.nom); cstmt.execute(); System.out.println("modification faite"); return resultat; Si nous regardons de plus près cette méthode, nous remarquons cette ligne : CallableStatement cstmt = cnx.preparecall("{call majgenre(?,?)"); RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 12

En fait, cette méthode JAVA va appeler une procédure PLSQL. Cette méthode PLSQL va à son tour appeler une méthode déclarée dans notre type SQL : genre_type. Voici la procédure PLSQL : create or replace procedure majgenre(nom in varchar2) is genr genre_type; begin select value(g) into genr from genre g where g.numgenre=self.num; genr.updategenre(nom); END; Et le corps de la méthode updategenre : CREATE OR REPLACE TYPE BODY genre_type AS INSTANTIABLE FINAL MEMBER PROCEDURE updategenre(nomg in varchar2) IS begin update genre set nom=nomg where numgenre=self.numgenre; end updategenre; Suppression d un genre La suppression d un genre est strictement identique à la modification. Il doit choisir le genre à supprimer et cliquer sur le bouton supprimer. Voila pourquoi nous ne copierons pas le code. En revanche, nous mettrons tout ce code en ANNEXE B. (Code de la classe JAVA) Pour finir, voici à quoi ressemble notre interface : Administration des photos RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 13

L administration des photos est un peu particulier car c est à partir d ici que nous allons enregistrer notre image dans la base de données. Nous nous intéresserons uniquement l enregistrement de photo et à sa suppression. Enregistrement d une photo Dans un premier temps, nous décrirons la démarche à suivre : - Remplissage des différents champs (format de la photo, description, mots clés,...) - Possibilité de lier la photo à un acteur etou un film - Choisir la photo à ajouter (depuis notre machine) - Ajout de la photo (attributs + image) dans la base de données Techniquement, cela se passe de cette façon : Instancie un objet de type Photo en initialisant les différents attributs à partir des informations saisies Insertions des données textuelles dans notre base de données Insertion dans les tables imbriquées si nécessaire. (table FILM etou ACTEUR) Rafraichissement du tableau contenant la liste des images dans notre base de données. chargement de l'image choisie dans la base de données via un objet de type ORDImage et la méthode setoradata On dissocie l enregistrement des données textuelles de l enregistrement de la photo proprement dite. Pour l enregistrement des données textuelles, nous utiliserons la méthode enregistrer de l objet Photo. Pour l enregistrement de la photo dans la base de données, nous utiliserons la méthode chargement. L enregistrement des données textuelles est tout ce qu il y a de plus basique, nous utilisons permet une d'enregistrer requête INSERT INTO. une photo En revanche, nous devons vérifier si la photo est liée à un acteur ou à un public film boolean car si c est enregistrer() le cas, nous devons throws insérer SQLException{ la photo dans la table imbriquée de la table boolean resultat = false; correspondante. Connection cnx = BDM_projetView.connect; this.numero = this.getnewid(); String newphoto; insertion dans la table photo if (this.film==0 && this.acteur==0){ newphoto="insert into photo(numphoto,nom,taille,format,description,mot_cles,image,signature) values("+this.numero+",'"+nom+"',"+this.taille+",'"+this.format+"','"+this.description+"', '"+this.motscles+"',ordsys.ordimage.init(),ordsys.ordimagesignature.init())"; else{ RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 14 if (this.film==0 && this.acteur>0){ newphoto="insert into photo(numphoto,nom,taille,format,description,mot_cles,acteurp,image,signature)

PreparedStatement stp = cnx.preparestatement(newacteurphoto); if(stp.executeupdate()!= 1){ resultat=false; else{ resultat=true; System.out.println("ajout de la la photo à l'acteur confirmée"); stp.close(); reconstruction de l'index de mot clés qui sert pour intermedia text String RAPPORT index DE BASE ="ALTER DE DONNEES index motcles_index MULTIMEDIA III rebuild";mise Partie conception de à l application jour de l'index 15 de texte "mot_index" PreparedStatement stp = cnx.preparestatement(index);

A ce stade, nous avons établi le lien entre la photo et les autres tables (FILM et ACTEUR), en revanche, l objet multimédia ORDSYS.ORDImage est encore vide. Nous allons donc voir la méthode qui permet l ajout de l image. methode du chargement d'un fichier de la photo dans l'ordimage public void chargement(string nomfichier, int idphoto) throws IOException{ charge l'image quie est dans nomfichier, dans la photo d'ienditifiant idphoto generation des paquets et de la signature de l'image connexion a la base byte[] ctx[] = new byte[4000][1];pour la generation de la signature OrdImage imgobj; OrdImageSignature sig; try{ recuperation des attributs image et imagesig pour la photo idphoto Connection conn=bdm_projetview.connect; conn.setautocommit(false); Statement stmt = conn.createstatement(); String req = "SELECT image,signature FROM photo WHERE numphoto="+idphoto+" FOR UPDATE"; OracleResultSet rs = (OracleResultSet) stmt.executequery(req); while(rs.next()){ imgobj = (OrdImage) rs.getoradata(1, OrdImage.getORADataFactory()) ; sig = (OrdImageSignature) rs.getoradata(2, generation des propriétés (meta données de l'objet java) OrdImageSignature.getORADataFactory() ); imgobj.setproperties(); this.image=imgobj; generation de la signature de l'image chargement du fichier dans l'ordimage (java) sig.generatesignature(imgobj); Envoi de l'image dans l'attribut localdata du type ORDImage mise a jour de la base avec les objets java imgobj.loaddatafromfile(nomfichier); image generation des propriétés (meta données de l'objet java) imgobj.setproperties(); String req2 = "UPDATE photo SET image =? WHERE numphoto = "+idphoto; generation de la signature de l'image OraclePreparedStatement opst = (OraclePreparedStatement) sig.generatesignature(imgobj); conn.preparecall(req2); mise a jour de la base avec les objets java opst.setoradata(1, imgobj); image opst.execute(); signature String req2 "UPDATE photo SET image =? WHERE numphoto = "+idphoto; RAPPORT String DE req3 BASE = DE "UPDATE DONNEES photo MULTIMEDIA SET signature III Partie = conception? WHERE de numphoto l application = "+idphoto; 16 OraclePreparedStatement opst = (OraclePreparedStatement) OraclePreparedStatement opst2 = (OraclePreparedStatement) conn.preparecall(req2); conn.preparecall(req3); opst.setoradata(1, imgobj);

Avec cette méthode, nous avons maintenant notre image stockée dans notre base de données. Nous pourrons par la suite l utiliser pour la comparer à d autres images présentes dans notre base. Suppression d une photo Si nous n avions qu à supprimer la photo sans se soucier des relations, nous aurions pu utiliser une simple requête DELETE, en effet celle-ci s occupera de supprimer toutes les données textuelles mais l objet multimédia également. Cependant, n oublions pas que notre photo est présente dans la table photo, mais elle est susceptible d exister également dans les tables imbriquées d ACTEUR et FILM. Pour la suppression de la photo en elle même, nous utiliserons la requête suivante : String delphoto="delete FROM photo p where p.numphoto="+this.numero; Et pour la suppression dans les tables imbriquées, nous utiliserons une requête de type DELETE FROM THE String delacteurimbriquee="delete FROM the (select acteur.photoa from acteur a WHERE a.numacteur ="+this.acteur + ") p where DEREF(p.photoR).numphoto="+this.numero; Une fois nos requêtes construites, nous n avons plus qu a les exécuter via un objet PreparedStatement. Notons qu il faut d abord supprimer dans les tables imbriquées avant de supprimer dans la table photo. Voici l interface pour la gestion des photos : RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 17

Partie Utilisateur La partie utilisateur représente en réalité l exploitation de la base de données. Nous devons permettre à l utilisateur de retrouver des films, acteurs, ou photos en fonction de critères spécifiques, ou en comparant deux éléments de notre base de données (Deux images) Recherche de film La recherche de films est plutôt basique, l utilisateur a à sa disposition plusieurs moyens pour retrouver un film : - Par le numéro de film - Par son nom - Par sa durée Une fois la recherche lancée, le programme va afficher à l écran tous les films correspondant dans un tableau. Pour chaque film, il peut y avoir plusieurs photos associées. Nous avons donc mis une liste déroulante pour visualiser les différentes images associées à ce film. RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 18

Pour mettre à jour notre liste, nous utilisons la table imbriquée contenant la liste des photos. A chaque changement sur la liste déroulante, nous mettons à jour la photo affichée à l écran. De plus, nous avons des informations liées au film qui s affiche sur le JPanel. Le code n étant pas très excitant, nous allons uniquement afficher les requêtes utilisées pour la récupération des films. if (dur==0) maxid = "select f.numfilm,f.nom,f.duree,deref(f.genref).numgenre,f.photof from film f where numfilm like '%"+ numero+"%' and nom like '%"+ nom+"%'"; else maxid = "select f.numfilm,f.nom,f.duree,deref(f.genref).numgenre,f.photof from film f where numfilm like '%"+ numero+"%' and nom like '%"+ nom+"%' and duree like '%"+ dur+"%' "; Voici une capture d écran pour la recherche d un film : RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 19

Recherche textuelle de photos La recherche de photo, c est un peu le même principe qu au dessus, il n y a rien de très innovant et très intéressant dans le code proprement dit. Pour la rechercher, nous allons uniquement utiliser les informations textuelles de la photo pour proposer à l utilisateur des photos susceptible de correspondre à sa recherche. C est pourquoi nous n allons pas mettre de code, mais nous allons expliquer à partir de quel critère nous pouvons retrouver une photo : - Son numéro d identification, - Son nom, - Sa taille, - Son format (JPG, PNG, GIF,...) - Sa description, - Et enfin mots-clés. Cela n a donc rien de nouveau par rapport aux bases de données relationnelles, la requête retourne uniquement des lignes que nous affichons directement dans le tableau. Le seul aspect intéressant est comment on récupère la photo de notre base de données et comment l affiche t on à l écran. Dans le cas qui va suivre, la méthode va récupérer toute les photos et retourner un tableau de CPhoto permet d'obtenir toutes les photos public static Cphoto[] getall() throws SQLException{ int i=0; int nbphoto = Cphoto.getNbPhoto(); Cphoto[] listep = new Cphoto[nbPhoto]; OrdImage imgobj; String maxid = "Select numphoto,nom,taille,format,description,mot_cles, DEREF(acteurP).numacteur,DEREF(filmP).numfilm,image FROM photo ORDER BY numphoto"; PreparedStatement stmax = BDM_projetView.connect.prepareStatement(maxId); OracleResultSet rset = (OracleResultSet)stmax.executeQuery(); while(rset.next()){ imgobj = (OrdImage) rset.getoradata(9, OrdImage.getORADataFactory()) ; listep[i] = new Cphoto(rset.getInt(1), rset.getstring(2),rset.getint(3), rset.getstring(4),rset.getstring(5), rset.getstring(6),rset.getint(7),rset.getint(8),imgobj); i++; return listep; i++; return listep; RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 20

La ligne qui nous intéresse pour récupérer notre objet photo directement depuis notre base de données est celle-ci : imgobj = (OrdImage) rset.getoradata(9, OrdImage.getORADataFactory()) ; Le premier paramètre est le numéro de colonne ou se trouve notre objet ORDImage, et la méthode getoradatafactory() récupère la l image réelle. Enfin, pour afficher notre image dans un composant graphique JAVA, nous avons créé une méthode dans notre classe CPhoto ou nous passons en argument le composant à modifier : affiche une image avec en paramètre un objet de type photo public void afficher2(jlabel pan,string nomfichier) throws IOException{ try { affiche la photo dans le JPanel pan --> on recupère l'ordimage, on le met dans un fichier intermédiaire, et on l'affiche on recupère l'ordimage on ecrit dans le fichier intermediaire System.out.println(nomfichier); this.image.getdatainfile(nomfichier); System.out.println("entrer"); catch (SQLException ex) { Logger.getLogger(Cphoto.class.getName()).log(Level.SEVERE, null, ex); System.out.println("entrer2"); img attribut de la classe de type Image Icon flageu = new ImageIcon(nomfichier); ImageIcon icone = new ImageIcon(nomfichier); Image imag=icone.getimage(); System.out.println("entre2r"); Image imag2=imag.getscaledinstance(200,200,imag.scale_default); System.out.println("oki"); ImageIcon icone2 = new ImageIcon(imag2); System.out.println("oki"); pan.seticon(icone2); Recherche d acteur et de genre Ces modules sont très similaires à ce que nous avons vu précédemment (Film et photo). Il est inutile de revoir ce qui as déjà été vu. Comparaison de deux images La comparaison d images permet de savoir si deux images sont similaires. Pour mettre en œuvre cette technique, nous utiliserons deux méthodes déjà définies dans ORDImage et ORDImageSignature. RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 21

La première méthode est EvaluateScore() qui nous permet de comparer deux images entre elles. Cette méthode évalue leur ressemblance et retourne un score entre 0 et 100 La seconde est issimilar. Cette méthode en plus de comparer deux images, prend un seuil en paramètre et nous retourne 0 ou 1 (0 si le seuil n est pas atteint, 1 sinon) Nous pouvons évaluer le score entre deux images en fonction de 3 critères : - En fonctions des formes, - Des textures, - Et des couleurs. Chacun de ces critères est modifiable via un slider qui renvoi une valeur entière entre 0 et 100. Enfin, nous avons également donné la possibilité à l utilisateur de modifier la valeur du seuil. Cette modification se fait également via un slider. Enfin, il ne reste plus qu à choisir deux images via une liste déroulante, et de comparer celles ci. Techniquement, c est un peu différent. Voici les étapes de l algorithme. Récupération des signatures des deux images via ORDSignatureImage Création de la commande de comparaison en fonction des valeurs des sliders Utilisation de cette commande avec EvalutateScore Récuperation du seuil en plus pour la méthode IsSimilar En java, cela se traduit de cette façon : - Récupération des signatures : String sql1 = "SELECT signature FROM photo WHERE numphoto="+ image1+ " FOR UPDATE"; Exécution et récupération du résultat des requêtes OracleResultSet rset = (OracleResultSet) stmt.executequery(sql1); Déclaration des instances de l'objet OrdImageSignature OrdImageSignature signature1 = null; Récupération du descripteur de l'ordimagesignature de l'image 1 signature1 = (OrdImageSignature) rset.getoradata(1, OrdImageSignature.getORADataFactory()); - Création de la commande en fonction des critères : commande="color="+(float)this.couleurs100 + " texture="+ (float)this.textures100+" shape="+ (float)this.formes100+" location=0"; - Récupération du résultat d evaluatescore : Comparaison par la méthode issimilar() int similaire = OrdImageSignature.isSimilar(signature1,signature2, commande,seuil); RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 22

Pour l utilisation de la méthode issimilar, il nous faut juste le seuil en plus : Comparaison par la méthode issimilar() int similaire = OrdImageSignature.isSimilar(signature1,signature2, commande,seuil); Une fois toutes ces actions effectuées, nous pouvons désormais afficher à l écran les résultats obtenus. Voila comment la fenêtre se présente a l utilisateur : RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 23

Similarité d image La similarité d images, c est le même principe qu au dessus a une différence près. On compare une image avec toutes les images de notre base de données. L utilisateur a également le choix pour la valeur des critères ainsi que du seuil. Nous avons donc créé une méthode qui nous retourne un tableau de CPhoto. Toutes les photos retournées seront donc en dessous du seuil défini par l utilisateur. Une fois notre tableau de CPhoto récupérer, alors nous mettons à jour notre tableau. Lorsque nous cliquons sur une ligne du tableau, la photo correspondante s affiche à l écran. Voici une capture d écran du résultat final : Intermedia Text Intermedia Text est nouveau pour nous. C est un module oracle qui nous donne la possibilité de gérer de façon assez facile les attributs de type texte et de pouvoir effectuer des recherches sur ces textes. Remarquons que pour pouvoir utiliser Intermédia Text, nous devons avoir une clé primaire sur notre table et créer un index de texte sur la colonne contenant la description textuelle. Cet index est nécessaire si Intermédia Text veut offrir de bonnes performances. Pour utiliser Intermedia Text, il faut utiliser le mot-clé CONTAINS dans notre requête SQL. RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 24

Dès lors, différentes solutions de recherches s offrent à nous : - Recherche par correspondance exacte, - Recherche par correspondance exacte de plusieurs mots combinés - Recherche par proximité de mots - Par radical de mot - Par rapprochement orthographique - Et enfin par rapprochement sonore. En fonction du critère choisi, notre code SQL dans CONTAINS sera modifié. Voici un tableau récapitulatif des opérateurs de CONTAINS : Critère Mot exact Partie de mot Même racine Orthographe proche Son proche Mot proche Deux mots exacts Opérateur Aucun opérateur mot % $ mot! mot? mot mot1 NEAR mot2 mot1 ACCUM mot2 Notre requête devra donc être modifiée en fonction du critère. Une fois la requête écrite, nous l exécutons, et nous récupérons une liste de CPhoto. Liste que nous exploiterons pour mettre à jour notre tableau. Comme d habitude, si l utilisateur veut voir la photo, il devra cliquer sur une ligne du tableau. Voici le code de la méthode qui nous permet de récupèrer la liste de CPhoto : permet de trouver les enregistrements qui correspondent avec la méthode intermedia TEXT on crée un index sur la colonne auparavant index dispo dans creation.sql public Cphoto[] intermediatext() throws SQLException{ int nbphoto = getnbphoto(); OrdImage imgobj ; String sql2=""; Cphoto[] listes = new Cphoto[nbPhoto]; Connection conn=bdm_projetview.connect; Statement stmt = conn.createstatement(); création de l'index pour intermedia Text; String sql1 ="create index motcles_index on photo(mot_cles) indextype is ctxsys.context;"; if (criteres=="mot RAPPORT DE BASE exact"){ DE DONNEES MULTIMEDIA III Partie conception de l application 25 sql2 = "SELECT signature,image,numphoto,nom,taille,format,description,mot_cles,deref(acteurp).numacteur,d EREF(filmP).numfilm FROM photo WHERE CONTAINS(mot_cles,'"+this.mot1+"')>0";

if (criteres=="mot exact"){ sql2 = "SELECT signature,image,numphoto,nom,taille,format,description,mot_cles,deref(acteurp).numacteur,d EREF(filmP).numfilm FROM photo WHERE CONTAINS(mot_cles,'"+this.mot1+"')>0"; if (criteres=="partie de mot"){ sql2 = "SELECT signature,image,numphoto,nom,taille,format,description,mot_cles,deref(acteurp).numacteur,d EREF(filmP).numfilm FROM photo WHERE CONTAINS(mot_cles,'"+this.mot1+"%')>0"; if (criteres=="même racine"){ sql2 = "SELECT signature,image,numphoto,nom,taille,format,description,mot_cles,deref(acteurp).numacteur,d EREF(filmP).numfilm FROM photo WHERE CONTAINS(mot_cles,'$"+this.mot1+"')>0"; if (criteres=="orthographe proche"){ sql2 = "SELECT signature,image,numphoto,nom,taille,format,description,mot_cles,deref(acteurp).numacteur,d EREF(filmP).numfilm FROM photo WHERE CONTAINS(mot_cles,'?"+this.mot1+"')>0"; if (criteres=="son proche"){ sql2 = "SELECT signature,image,numphoto,nom,taille,format,description,mot_cles,deref(acteurp).numacteur,d EREF(filmP).numfilm FROM photo WHERE CONTAINS(mot_cles,'!"+this.mot1+"')>0"; if (criteres=="mots proches"){ sql2 = "SELECT signature,image,numphoto,nom,taille,format,description,mot_cles,deref(acteurp).numacteur,d EREF(filmP).numfilm FROM photo WHERE CONTAINS(mot_cles,'"+this.mot1+" NEAR "+this.mot2+"')>0"; if (criteres=="deux mots exacts"){ sql2 = "SELECT signature,image,numphoto,nom,taille,format,description,mot_cles,deref(acteurp).numacteur,d EREF(filmP).numfilm FROM photo WHERE CONTAINS(mot_cles,'"+this.mot1+" ACCUM "+this.mot2+"')>0"; Exécution et récupération du résultat de la requête System.out.println(sql2); OracleResultSet rset2 = (OracleResultSet) stmt.executequery(sql2); int i=0; while(rset2.next()){ imgobj = (OrdImage) rset2.getoradata(2, OrdImage.getORADataFactory()); listes[i] = new Cphoto(rset2.getInt(3), rset2.getstring(4),rset2.getint(5), rset2.getstring(6),rset2.getstring(7), rset2.getstring(8),rset2.getint(9),rset2.getint(10),imgobj); i++; System.out.println(i); stmt.close(); return listes; Cette méthode nous permet donc d avoir à notre disposition l ensemble des photos répondant aux critères. RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 26

Voici comment se présente de résultat pour l utilisateur : Thesaurus Thesaurus, c est une autre façon d effectuer des recherches sur les textes. Un Thésaurus est un vocabulaire de termes qui ont entre eux des relations sémantiques (qui ont un sens donc) et génériques. Il y a trois types de relations gérés par Thésaurus : - Relations hiérarchique (animal > oiseaux), - Equivalence (voiture = automobile) - Et association (pilote & course) Pour pouvoir mettre en œuvre Thésaurus, il faut au préalable en créer un (un vocabulaire de termes mis en relation entre eux). La création de notre thésaurus se trouve en «ANNEXE C». Pour utiliser un type de relation en particulier, nous utiliserons trois mots clé : - BT => terme plus général - NT => plus spécifique - SYN => Synonyme Une fois notre thesaurus terminé, nous pouvons exploiter celui avec le mot clé CONTAINS (oui, c est le même que pout Intermedia Text). Nous avons donc plus qu à écrire notre requête SQL et l exécuter. RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 27

Voici le code de la méthode thesaurus de notre classe CPhoto. permet de trouver les enregistrements qui correspondent avec la méthode thesaurus le thesaurus est créé avant l'index sur description est créé avant aussi public Cphoto[] listethesaurus() throws SQLException{ int nbphoto = getnbphoto(); OrdImage imgobj ; String sql2 = null; Cphoto[] listes = new Cphoto[nbPhoto]; Connection conn=bdm_projetview.connect; Statement stmt = conn.createstatement(); if (this.criteres=="nt"){ sql2= "SELECT signature,image,numphoto,nom,taille,format,description,mot_cles,deref(acteurp).numacteur,d EREF(filmP).numfilm, score (100) FROM PHOTO WHERE CONTAINS (description, ctx_thes.nt('"+this.mot1+"',"+this.niveau+",'thesaurus_photo'), 100) > 0 "; if (this.criteres=="bt"){ sql2= "SELECT signature,image,numphoto,nom,taille,format,description,mot_cles,deref(acteurp).numacteur,d EREF(filmP).numfilm, score (100) FROM PHOTO WHERE CONTAINS (description, ctx_thes.bt('"+this.mot1+"',"+this.niveau+",'thesaurus_photo'), 100) > 0 "; if (this.criteres=="syn"){ sql2= "SELECT signature,image,numphoto,nom,taille,format,description,mot_cles,deref(acteurp).numacteur,d EREF(filmP).numfilm, score (100) FROM PHOTO WHERE CONTAINS (description, ctx_thes.syn('"+this.mot1+"','thesaurus_photo'), 100) > 0 "; Exécution et récupération du résultat de la requête OracleResultSet rset2 = (OracleResultSet) stmt.executequery(sql2); int i=0; while(rset2.next()){ imgobj = (OrdImage) rset2.getoradata(2, OrdImage.getORADataFactory()); listes[i] = new Cphoto(rset2.getInt(3), rset2.getstring(4),rset2.getint(5), rset2.getstring(6),rset2.getstring(7), rset2.getstring(8),rset2.getint(9),rset2.getint(10),imgobj,rset2.getint(11)); i++; stmt.close(); return listes; Et la comme toujours, nous exploitons notre liste de CPhoto et mettons à jour notre tableau. L affichage de la photo se fait lors du clique sur une ligne du tableau. RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 28

Pour finir, voici une capture d écran de notre interface (page suivante): RAPPORT DE BASE DE DONNEES MULTIMEDIA III Partie conception de l application 29

IV Conclusion Améliorations Notre application bien qu elle soit fonctionnelle et réponde aux critères du cahier des charges peut être sensiblement améliorée. Voici une liste d améliorations auxquelles nous avons pensé - Système de recherche plus élaboré (critères supplémentaires,...) - Optimisation du code (aussi bien en JAVA qu en SQL (optimisation de requêtes)) - Avoir la possibilité d avoir plusieurs acteurs par photo - Mettre des extraits vidéo et sonores Et si on recommençait? Une autre façon d appréhender le sujet était en réalité de réaliser tous les traitements avec SQL. En effet, au lieu de faire toutes nos modifications via nos classes JAVA, une autre possibilité était de délaisser le traitement en JAVA et de tout faire en PLSQL via des méthodes dans nos types SQL. Ainsi, nous n aurions eu qu à appeler ces méthodes en JAVA et analyser le résultat. Conclusion générale Pour terminer, ce projet qui nous a été donné a été autant instructif qu intéressant. En effet, nous avons pu mettre en œuvre de nouvelles techniques permettant le stockage de données (stockage d objets multimédia). Nous avons également pu acquérir de nouvelle méthodes de recherche pour des descriptions textuelles. Thesaurus a un réel intérêt dans la mesure où la recherche ne se fait plus uniquement en comparant deux chaînes de caractères, mais plutôt en comparant leur sémantique. Chose qui est impossible sans cela. Concernant Intermedia Text, la recherche est tout aussi poussée, mais exclue la sémantique de la chaîne. Même si ce projet fut très intéressant, il semblerait que les bases de données multimédia ne soient dominantes pas sur le parc informatique. En revanche, cela pourrait bien constituer un véritable atout pour notre future vie professionnelle. RAPPORT DE BASE DE DONNEES MULTIMEDIA IV Conclusion 30

ANNEXES ANNEXE A Création Base + Types + insertion drop type genre_type force; drop type film_type force; drop type acteur_type force; drop type filmacteur_type force; drop type photo_type force; drop type photo_ref_type force; drop type film_ref_type force; drop type films_type force; drop type photos_type force; create type genre_type ; create type film_type ; create type acteur_type ; create type filmacteur ; create type photo_type; create type photo_ref_type ; create type film_ref_type; --collection de references sur photo create type photo_ref_type AS OBJECT( photor REF photo_type ); create type photos_type as TABLE of photo_ref_type; --collection de r 馥 rences sur film create type film_ref_type as object( filmr REF film_type ); create type films_type as TABLE of film_ref_type; --creation des types create type genre_type as OBJECT( numgenre integer, nom varchar2(100), filmg films_type, INSTANTIABLE FINAL MEMBER procedure updategenre(num in integer, nomg in varchar2), INSTANTIABLE FINAL MEMBER procedure suppgenre(num in integer)) INSTANTIABLE FINAL; create type film_type as OBJECT( numfilm integer, nom varchar2(100), duree integer, genref REF genre_type, photof photos_type ); RAPPORT DE BASE DE DONNEES MULTIMEDIA ANNEXES 31 create type acteur_type as OBJECT( numacteur integer,

create type film_type as OBJECT( numfilm integer, nom varchar2(100), duree integer, genref REF genre_type, photof photos_type ); create type acteur_type as OBJECT( numacteur integer, nom varchar2(100), prenom varchar2(100), photoa photos_type, INSTANTIABLE FINAL MEMBER procedure updateacteur(num in integer, noma in varchar2,pre in varchar2), INSTANTIABLE FINAL MEMBER procedure suppacteur(num in integer)) INSTANTIABLE FINAL; create type filmacteur_type as OBJECT ( idfilmacteur integer, filma REF film_type, acteurf REF acteur_type ); create type photo_type as OBJECT( numphoto integer, nom varchar2(100), taille integer, format varchar2(10), description varchar2(200), mot_cles varchar2(200), signature ORDSYS.ORDImageSignature, image ORDSYS.ORDImage, extrait ORDSYS.ORDVideo, acteurp REF acteur_type, filmp REF film_type ); drop table genre; drop table acteur; drop table film; drop table photo; drop table film_acteur; --creation des tables---------------------- create table genre of genre_type( primary key(numgenre)) nested table filmg store as tabfilmg; create table film of film_type( primary key(numfilm), genref scope is genre) nested table photof store as tabphotosf; create table acteur of acteur_type( primary key (numacteur)) nested table photoa store as tabphotoa; create table film_acteur of filmacteur_type( primary key(idfilmacteur), filma scope is film, acteurf scope is acteur ); create table photo of photo_type( primary key(numphoto), acteurp scope is acteur, filmp scope is film RAPPORT DE BASE DE DONNEES MULTIMEDIA ANNEXES 32 );

create table photo of photo_type( primary key(numphoto), acteurp scope is acteur, filmp scope is film ); ------------------------------------------------------------- -- cr 顴 ion des m 鴨 odes du type genre et du type acteur----- ------------------------------------------------------------- CREATE OR REPLACE TYPE BODY genre_type AS INSTANTIABLE FINAL MEMBER PROCEDURE updategenre( nomg in varchar2) IS begin update genre set nom=nomg where numgenre=self.numgenre; end updategenre; INSTANTIABLE FINAL MEMBER PROCEDURE suppgenre() IS begin delete from genre where numgenre=self.numgenre; end suppgenre; END; show errors CREATE OR REPLACE TYPE BODY acteur_type AS INSTANTIABLE FINAL MEMBER procedure updateacteur( noma in varchar2,pre in varchar2) IS begin update acteur set nom=noma,prenom=pre where numacteur=self.numacteur; end updateacteur; INSTANTIABLE FINAL MEMBER PROCEDURE suppacteur() IS begin delete from acteur where numacteur=self.numacteur; end suppacteur; END; show errors create or replace procedure majgenre( num in integer,nom in varchar2) is genr genre_type; begin select value(g) into genr from genre g where g.numgenre=num; genr.updategenre(num,nom); END; show errors; create or replace procedure supressiongenre(num in integer) is genr genre_type; begin select value(g) into genr from genre g where g.numgenre=num; genr.suppgenre(num); END; show errors; --SET SERVEROUTPUT ON --execute supressiongenre(10); --execute majgenre(1,'action'); create or replace procedure majacteur( num in integer,nom in varchar2,pre in varchar2) is act acteur_type; begin select value(a) into act from acteur RAPPORT a where DE BASE a.numacteur=num; DE DONNEES MULTIMEDIA ANNEXES 33 act.updateacteur(num,nom,pre); END;

create or replace procedure majacteur( num in integer,nom in varchar2,pre in varchar2) is act acteur_type; begin select value(a) into act from acteur a where a.numacteur=num; act.updateacteur(num,nom,pre); END; show errors; create or replace procedure supressionacteur(num in integer) is act acteur_type; begin select value(a) into act from acteur a where a.numacteur=num; act.suppacteur(num); END; show errors; --execute supressionacteur(10); --execute majacteur(1,'bruce',lee'); ------------------------------------------- -- supression des tables existantes----- ------------------------------------------- drop table genre; drop table acteur; drop table film; drop table photo; drop table film_acteur; --creation des tables---------------------- create table genre of genre_type( primary key(numgenre)) nested table filmg store as tabfilmg; create table film of film_type( primary key(numfilm), genref scope is genre) nested table photof store as tabphotosf; create table acteur of acteur_type( primary key (numacteur)) nested table photoa store as tabphotoa; create table film_acteur of filmacteur_type( primary key(idfilmacteur), filma scope is film, acteurf scope is acteur ); create table photo of photo_type( primary key(numphoto), acteurp scope is acteur, filmp scope is film ); -- insertion de valeurs dans la base --insertion de valeurs dans genre drop sequence seq_genre; drop sequence seq_film; drop sequence seq_acteur; drop sequence seq_filmacteur; drop sequence seq_photo; create sequence seq_genre; create sequence seq_film; create sequence seq_acteur; create sequence seq_filmacteur; RAPPORT DE BASE DE DONNEES MULTIMEDIA ANNEXES 34

create sequence seq_genre; create sequence seq_film; create sequence seq_acteur; create sequence seq_filmacteur; create sequence seq_photo; insert into genre values(seq_genre.nextval,'action',films_type()); insert into genre values(seq_genre.nextval,'aventure',films_type()); insert into genre values(seq_genre.nextval,'romantique',films_type()); insert into genre values(seq_genre.nextval,'animation',films_type()); insert into genre values(seq_genre.nextval,'thriller',films_type()); --insertion de valeurs dans film insert into film values( seq_film.nextval,'bandidas',160,(select ref(g) from genre g where numgenre=1),photos_type()); insert into film values( seq_film.nextval,'indiana jones',120,(select ref(g) from genre g where numgenre=2),photos_type()); insert into film values( seq_film.nextval,'double face',95,(select ref(g) from genre g where numgenre=1),photos_type()); insert into film values( seq_film.nextval,'incassable',90,(select ref(g) from genre g where numgenre=3),photos_type()); insert into film values( seq_film.nextval,'lucky luke',84,(select ref(g) from genre g where numgenre=4),photos_type()); insert into film values( seq_film.nextval,'indiana jones',75,(select ref(g) from genre g where numgenre=1),photos_type()); insert into film values( seq_film.nextval,'barbie',20,(select ref(g) from genre g where numgenre=1),photos_type()); insert into film values( seq_film.nextval,'black Swan ',95,(select ref(g) from genre g where numgenre=3),photos_type()); insert into film values( seq_film.nextval,'xmen',100,(select ref(g) from genre g where numgenre=5),photos_type()); insert into film values( seq_film.nextval,'fast and Furious 5',95,(select ref(g) from genre g where numgenre=1),photos_type()); insert into film values( seq_film.nextval,'le discours d un roi',100,(select ref(g) from genre g where numgenre=2),photos_type()); insert into film values( seq_film.nextval,'fast and Furious 5',95,(select ref(g) from genre g where numgenre=1),photos_type()); insert into film values( seq_film.nextval,'trop loin pour toi',100,(select ref(g) from genre g where numgenre=3),photos_type()); insert into film values( seq_film.nextval,'n oublie jamais',80,(select ref(g) from genre g where numgenre=3),photos_type()); insert into film values( seq_film.nextval,'la ferme se rebelle',115,(select ref(g) from genre g where numgenre=4),photos_type()); --insertion de valeurs dans acteur insert into acteur values (seq_acteur.nextval,'penelope', 'cruz',photos_type()); insert into acteur values (seq_acteur.nextval,'nicolas', 'cage',photos_type()); insert into acteur values (seq_acteur.nextval,'john', 'travolta',photos_type()); insert into acteur values (seq_acteur.nextval,'vin ', 'diesel',photos_type()); insert into acteur values (seq_acteur.nextval,'monica', 'belucci',photos_type()); insert into acteur values (seq_acteur.nextval,'joe', 'dalton',photos_type()); insert into acteur values (seq_acteur.nextval,'penelope', 'cruz',photos_type()); insert into acteur values (seq_acteur.nextval,'helena ', 'Bonham Carter',photos_type()); insert into acteur values (seq_acteur.nextval,'natalie', 'portman',photos_type()); insert into acteur values (seq_acteur.nextval,'vin ', 'diesel',photos_type()); insert into acteur values (seq_acteur.nextval,'tom', 'dalton',photos_type()); insert into acteur values (seq_acteur.nextval,'mila', 'Mila Kunis',photos_type()); insert into acteur values (seq_acteur.nextval,'drew', 'Barrymore',photos_type()); insert into acteur values (seq_acteur.nextval,'paul', 'Walker',photos_type()); --insertion de valeurs dans film_acteur insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=1),(select ref(a) from acteur a where numacteur=1)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=1),(select ref(a) from acteur a where numacteur=5)); RAPPORT DE BASE DE DONNEES MULTIMEDIA ANNEXES 35 insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=7),(select ref(a) from acteur a where numacteur=5)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where

insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=7),(select ref(a) from acteur a where numacteur=5)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=8),(select ref(a) from acteur a where numacteur=8)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=8),(select ref(a) from acteur a where numacteur=9)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=1),(select ref(a) from acteur a where numacteur=5)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=2),(select ref(a) from acteur a where numacteur=4)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=14),(select ref(a) from acteur a where numacteur=12)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=14),(select ref(a) from acteur a where numacteur=12)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=12),(select ref(a) from acteur a where numacteur=4)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=12),(select ref(a) from acteur a where numacteur=14)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=11),(select ref(a) from acteur a where numacteur=8)); insert into film_acteur values (seq_filmacteur.nextval,(select ref(f) from film f where numfilm=15),(select ref(a) from acteur a where numacteur=2)); --ajout de film a un genre insert into the (select g.filmg FROM genre g WHERE g.numgenre=1) SELECT ref(f) FROM film f WHERE f.numfilm = 1; insert into the (select g.filmg FROM genre g WHERE g.numgenre=1) SELECT ref(f) FROM film f WHERE f.numfilm = 3; insert into the (select g.filmg FROM genre g WHERE g.numgenre=1) SELECT ref(f) FROM film f WHERE f.numfilm = 6; insert into the (select g.filmg FROM genre g WHERE g.numgenre=1) SELECT ref(f) FROM film f WHERE f.numfilm = 7; insert into the (select g.filmg FROM genre g WHERE g.numgenre=1) SELECT ref(f) FROM film f WHERE f.numfilm = 12; insert into the (select g.filmg FROM genre g WHERE g.numgenre=2) SELECT ref(f) FROM film f WHERE f.numfilm = 2; insert into the (select g.filmg FROM genre g WHERE g.numgenre=2) SELECT ref(f) FROM film f WHERE f.numfilm = 11; insert into the (select g.filmg FROM genre g WHERE g.numgenre=3) SELECT ref(f) FROM film f WHERE f.numfilm = 4; insert into the (select g.filmg FROM genre g WHERE g.numgenre=3) SELECT ref(f) FROM film f WHERE f.numfilm = 8; insert into the (select g.filmg FROM genre g WHERE g.numgenre=3) SELECT ref(f) FROM film f WHERE f.numfilm = 13; insert into the (select g.filmg FROM genre g WHERE g.numgenre=3) SELECT ref(f) FROM film f WHERE f.numfilm = 14; insert into the (select g.filmg FROM genre g WHERE g.numgenre=4) SELECT ref(f) FROM film f WHERE f.numfilm = 5; insert into the (select g.filmg FROM genre g WHERE g.numgenre=4) SELECT ref(f) FROM film f WHERE f.numfilm = 15; insert into the (select g.filmg FROM genre g WHERE g.numgenre=5) SELECT ref(f) FROM film f WHERE f.numfilm = 9; drop index motcles_index; create index motcles_index on photo(mot_cles) indextype is ctxsys.context; -- pour intermedia text drop index description_index; create index description_index on photo(description) indextype is ctxsys.context; -- pour thesaurus RAPPORT DE BASE DE DONNEES MULTIMEDIA ANNEXES 36

ANNEXE B package bdm_projet; import java.sql.*; import oracle.jdbc.oraclepreparedstatement; import oracle.jdbc.oracleresultset; public class Cgenre { public int numero; public String nom; public Cgenre(int num, String nom){ this.nom = nom; this.numero = num; public Cgenre(){ obtenir la liste de tous les genres public static Cgenre[] getall() throws SQLException{ int i=0; int nbgenre = Cgenre.getNbGenre(); Cgenre[] listeg = new Cgenre[nbGenre]; String maxid = "Select * FROM genre ORDER BY numgenre"; PreparedStatement stmax = BDM_projetView.connect.prepareStatement(maxId); OracleResultSet rset = (OracleResultSet)stmax.executeQuery(); while(rset.next()){ listeg[i] = new Cgenre(rset.getInt(1), rset.getstring(2)); i++; return listeg; donne le nombre de genre public static int getnbgenre() throws SQLException{ String maxid = "Select COUNT(numgenre) FROM genre"; PreparedStatement stmax = BDM_projetView.connect.prepareStatement(maxId); OracleResultSet rset=(oracleresultset) stmax.executequery(); rset.next(); return rset.getint(1); permet d'enregistrer un genre public boolean enregistrer() throws SQLException{ boolean resultat = false; Connection cnx = BDM_projetView.connect; this.numero = this.getnewid(); String newgenre="insert into genre values("+this.numero+",'"+nom+"',films_type())"; PreparedStatement st = cnx.preparestatement(newgenre); if(st.executeupdate()!= 1){ resultat=false; else{ resultat=true; System.out.println("ajout du film confirmée"); RAPPORT DE BASE DE DONNEES MULTIMEDIA ANNEXES 37 return resultat;

resultat=true; System.out.println("ajout du film confirmée"); return resultat; permet de supprimer un genre public boolean supprimer() throws SQLException{ boolean resultat = false; Connection cnx = BDM_projetView.connect; String delfilmgenre="delete FROM film where f.genref.numgenre="+this.numero; System.out.println(delfilmgenre); PreparedStatement stdel = cnx.preparestatement(delfilmgenre); try{ stdel.executeupdate(); catch(exception e){ stdel.close(); CallableStatement cstmt = cnx.preparecall("{call supressiongenre(?)"); cstmt.setint(1, this.numero); cstmt.execute(); System.out.println("suppression faite"); return resultat; utilisation de la procedure pour modifier le genre public boolean modifier() throws SQLException{ boolean resultat = false; Connection cnx = BDM_projetView.connect; CallableStatement cstmt = cnx.preparecall("{call majgenre(?,?)"); cstmt.setint(1, this.numero); cstmt.setstring(2, this.nom); cstmt.execute(); System.out.println("modification faite"); return resultat; obtenir le prochain id private int getnewid() throws SQLException{ String maxid = "Select MAX(numgenre) FROM genre"; PreparedStatement stmax = BDM_projetView.connect.prepareStatement(maxId); OracleResultSet rset=(oracleresultset) stmax.executequery(); rset.next(); return rset.getint(1)+1; RAPPORT DE BASE DE DONNEES MULTIMEDIA ANNEXES 38

ANNEXE C -- suppression d'un thesaurus BEGIN CTX_THES.DROP_Thesaurus('thesaurus_photo'); END; begin ctx_thes.create_thesaurus('thesaurus_photo', FALSE); END; --creation des phrases BEGIN ctx_thes.create_phrase('thesaurus_photo','film'); ctx_thes.create_phrase('thesaurus_photo','actrice'); ctx_thes.create_phrase('thesaurus_photo','s 鲩 e'); ctx_thes.create_phrase('thesaurus_photo','t 鬩 film'); ctx_thes.create_phrase('thesaurus_photo','acteur'); ctx_thes.create_phrase('thesaurus_photo','c 鬩 brit 駼 span>); ctx_thes.create_phrase('thesaurus_photo','c 鬩 bre'); ctx_thes.create_phrase('thesaurus_photo','muscl 駼 span>); ctx_thes.create_phrase('thesaurus_photo','gros bras'); ctx_thes.create_phrase('thesaurus_photo','mignonne'); ctx_thes.create_phrase('thesaurus_photo','belle'); ctx_thes.create_phrase('thesaurus_photo','r); ctx_thes.create_phrase('thesaurus_photo','personnage'); ctx_thes.create_phrase('thesaurus_photo','r); ctx_thes.create_phrase('thesaurus_photo','personnage'); ctx_thes.create_phrase('thesaurus_photo','meilleur'); ctx_thes.create_phrase('thesaurus_photo','bon'); ctx_thes.create_phrase('thesaurus_photo','bandidas'); ctx_thes.create_phrase('thesaurus_photo','western'); ctx_thes.create_phrase('thesaurus_photo','revolver'); ctx_thes.create_phrase('thesaurus_photo','bandidas'); ctx_thes.create_phrase('thesaurus_photo','western'); ctx_thes.create_phrase('thesaurus_photo','revolver'); ctx_thes.create_phrase('thesaurus_photo','cowboy'); ctx_thes.create_phrase('thesaurus_photo','sublime'); ctx_thes.create_phrase('thesaurus_photo','voitures'); ctx_thes.create_phrase('thesaurus_photo','ferrari'); ctx_thes.create_phrase('thesaurus_photo','porsche'); ctx_thes.create_phrase('thesaurus_photo','subaru'); ctx_thes.create_phrase('thesaurus_photo','amour'); ctx_thes.create_phrase('thesaurus_photo','romantique'); ctx_thes.create_phrase('thesaurus_photo','cheval'); ctx_thes.create_phrase('thesaurus_photo','animal'); ctx_thes.create_phrase('thesaurus_photo','jolly jumper'); ctx_thes.create_phrase('thesaurus_photo','action'); ctx_thes.create_phrase('thesaurus_photo','explosion'); ctx_thes.create_phrase('thesaurus_photo','corbeau'); ctx_thes.create_phrase('thesaurus_photo','armes'); ctx_thes.create_phrase('thesaurus_photo','arme'); ctx_thes.create_phrase('thesaurus_photo','r 鶯 lvers'); ctx_thes.create_phrase('thesaurus_photo','pistolet'); ctx_thes.create_phrase('thesaurus_photo','pistolets'); RAPPORT DE BASE DE DONNEES MULTIMEDIA ANNEXES 39 ctx_thes.create_phrase('thesaurus_photo','beau');

ctx_thes.create_phrase('thesaurus_photo','armes'); ctx_thes.create_phrase('thesaurus_photo','arme'); ctx_thes.create_phrase('thesaurus_photo','r 鶯 lvers'); ctx_thes.create_phrase('thesaurus_photo','pistolet'); ctx_thes.create_phrase('thesaurus_photo','pistolets'); ctx_thes.create_phrase('thesaurus_photo','beau'); END; -- creation des relations BEGIN CTX_THES.create_Relation('thesaurus_photo', 'film','nt','t 鬩 film'); CTX_THES.create_Relation('thesaurus_photo', 'film','nt','s 鲩 e'); CTX_THES.create_Relation('thesaurus_photo', 'romantique','bt','amour'); CTX_THES.create_Relation('thesaurus_photo', 'actrice','bt','c 鬩 brit 駼 span>); CTX_THES.create_Relation('thesaurus_photo', 'bandidas','nt','r 鶯 lver'); CTX_THES.create_Relation('thesaurus_photo', 'bandidas','nt','western'); CTX_THES.create_Relation('thesaurus_photo', 'meilleur','syn','bon'); CTX_THES.create_Relation('thesaurus_photo', 'bon','syn','beau'); CTX_THES.create_Relation('thesaurus_photo', 'mignonne','syn','belle'); CTX_THES.create_Relation('thesaurus_photo', 'personnage','syn','r); CTX_THES.create_Relation('thesaurus_photo', 'voitures','nt','porsche'); CTX_THES.create_Relation('thesaurus_photo', 'voitures','nt','ferrari'); CTX_THES.create_Relation('thesaurus_photo', 'voitures','nt','subaru'); CTX_THES.create_Relation('thesaurus_photo', 'action','nt','explosion'); CTX_THES.create_Relation('thesaurus_photo', 'animal','nt','cheval'); CTX_THES.create_Relation('thesaurus_photo', 'animal','nt','corbeau'); CTX_THES.create_Relation('thesaurus_photo', 'Jolly jumper','bt','animal'); CTX_THES.create_Relation('thesaurus_photo', 'western','nt','armes'); CTX_THES.create_Relation('thesaurus_photo', 'armes','nt','arme'); CTX_THES.create_Relation('thesaurus_photo', 'arme','nt','r 鶯 lvers'); CTX_THES.create_Relation('thesaurus_photo', 'arme','nt','pistolets'); CTX_THES.create_Relation('thesaurus_photo', 'r 鶯 lvers','nt','r 鶯 lver'); CTX_THES.create_Relation('thesaurus_photo', 'pistolets','nt','pistolet'); CTX_THES.create_Relation('thesaurus_photo', 'r 鶯 lvers','syn','pistolets'); CTX_THES.create_Relation('thesaurus_photo', 'r 鶯 lvers','syn','pistolet'); CTX_THES.create_Relation('thesaurus_photo', 'r 鶯 lver','syn','pistolets'); CTX_THES.create_Relation('thesaurus_photo', 'r 鶯 lver','syn','pistolet'); END; RAPPORT DE BASE DE DONNEES MULTIMEDIA ANNEXES 40