create_Variable : This function adds data to :class:`altimetry.data.hydro_data`
        
        :parameter name: name of the parameter to create
        :parameter value: values associated to the variable. Must be a numpy masked_array or a data structure.
        :parameter dimensions: dimensional structure (cf. notes).
        
        .. _structures:
        
        .. note:: altimetry tools package handles the NetCDF data using specific structures.
        
          NetCDF data is structured this way:
          
          .. code-block:: python
             :emphasize-lines: 1,3
           
             NetCDF_data = {'_dimensions':dimension_structure,  #File dimensions  (COMPULSORY)
                            '_attributes':attribute_structure,  #Global attributes
                            'dimension_1':data_structure,       #Data associated to the dimensions. (COMPULSORY)
                            ...,
                            'variable_1':data_structure,        #Variables
                            ...
                           }
          
          In standard NetCDF files, dimensions are always associated to a variable.
          If it is not the case, an array of indices the length of the dimension is generated and a warning is issued.
          
          Moreover, dimensions MUST be defined to be accepted by :class:`altimetry.tools.nctools.nc` (empty NetCDF files would fail).        
        
          * a dimensional structure should be of the form :
          
          .. code-block:: python
             
             dimension_structure = {'_ndims':N,        #Attribute setting the number of dimensions.
             
                                    'dims':{'dim_A':A, #Structure containing the name
                                            'dim_B':B, #of the dimensions and their size. 
                                            ...,
                                            'dim_N':N
                                           }
                                   }
          
          * an attribute structure is a very simple structure containing the attribute names and values:
        
          .. code-block:: python
              
              data_structure = {'attribute_1':attribute_1,
                                ...,
                                'attribute_N':attribute_N}
           
          * a data structure should be of the form :
        
          .. code-block:: python
              :emphasize-lines: 1-2
          
              data_structure = {'_dimensions':dimension_structure, #dimensions of hte variable (COMPULSORY)
                                'data':data,                       #data associated to the variable (COMPULSORY)
                                
                                'long_name':long_name,             #Variable attributes
                                'units':units,
                                ...
                               }
           
          
          DATA and _DIMENSIONS fields are compulsory.
          Other fields are optional and will be treated as attributes.
          
          Furthermore, code will have a special look at **scale**, **scale_factor** and **add_offset** while reading and writing data and to **_FillValue** and missing_value while reading (_FillValue being automatically filled by :class:`NetCDF4.Dataset` when writing)

def create_Variable(self,name,value,dimensions,toCreate=None,createDim=None,extend=True):
        """
        create_Variable : This function adds data to :class:`altimetry.data.hydro_data`
        
        :parameter name: name of the parameter to create
        :parameter value: values associated to the variable. Must be a numpy masked_array or a data structure.
        :parameter dimensions: dimensional structure (cf. notes).
        
        .. _structures:
        
        .. note:: altimetry tools package handles the NetCDF data using specific structures.
        
          NetCDF data is structured this way:
          
          .. code-block:: python
             :emphasize-lines: 1,3
           
             NetCDF_data = {'_dimensions':dimension_structure,  #File dimensions  (COMPULSORY)
                            '_attributes':attribute_structure,  #Global attributes
                            'dimension_1':data_structure,       #Data associated to the dimensions. (COMPULSORY)
                            ...,
                            'variable_1':data_structure,        #Variables
                            ...
                           }
          
          In standard NetCDF files, dimensions are always associated to a variable.
          If it is not the case, an array of indices the length of the dimension is generated and a warning is issued.
          
          Moreover, dimensions MUST be defined to be accepted by :class:`altimetry.tools.nctools.nc` (empty NetCDF files would fail).        
        
          * a dimensional structure should be of the form :
          
          .. code-block:: python
             
             dimension_structure = {'_ndims':N,        #Attribute setting the number of dimensions.
             
                                    'dims':{'dim_A':A, #Structure containing the name
                                            'dim_B':B, #of the dimensions and their size. 
                                            ...,
                                            'dim_N':N
                                           }
                                   }
          
          * an attribute structure is a very simple structure containing the attribute names and values:
        
          .. code-block:: python
              
              data_structure = {'attribute_1':attribute_1,
                                ...,
                                'attribute_N':attribute_N}
           
          * a data structure should be of the form :
        
          .. code-block:: python
              :emphasize-lines: 1-2
          
              data_structure = {'_dimensions':dimension_structure, #dimensions of hte variable (COMPULSORY)
                                'data':data,                       #data associated to the variable (COMPULSORY)
                                
                                'long_name':long_name,             #Variable attributes
                                'units':units,
                                ...
                               }
           
          
          DATA and _DIMENSIONS fields are compulsory.
          Other fields are optional and will be treated as attributes.
          
          Furthermore, code will have a special look at **scale**, **scale_factor** and **add_offset** while reading and writing data and to **_FillValue** and missing_value while reading (_FillValue being automatically filled by :class:`NetCDF4.Dataset` when writing)   
           
        """
        
        #Check variable name
        ####################
        #This allows to remove impossible variable names
        #!!!! This is not a good solution
        name=name.replace('.','_')
        
        #Check if data is structured or not
        isStructure = True if isinstance(value,dict) else False
        
        #Get dimensions
        dimName = np.array(dimensions.keys())
        dimVal = np.array(dimensions.values())
        keys=np.array(self._dimensions.keys())
        
#        if createDim is None : createDim = self._dimensions.has_key(dimName[0])
        createDim = np.array([not self._dimensions.has_key(dim) for dim in dimName]) if createDim is None else np.array(createDim)
        if toCreate is None : toCreate = np.sum(self.par_list == name) == 0
        
        self.message(3,'Loading {0} ({1}:{2}) from {3}'.format(name,dimName,dimVal,os.path.basename(self._filename)))

        #Cast variable into masked array first
        ######################################
        if (not isinstance(value['data'],np.ma.core.MaskedArray) if isStructure else not isinstance(value,np.ma.core.MaskedArray)) :
            value['data'] = np.ma.masked_array(value['data'],mask=np.zeros(tuple(dimVal),dtype='bool')) if isStructure else np.ma.masked_array(value,mask=np.zeros(tuple(dimVal),dtype='bool'))
            self.message(4,'Casting variable to np.ma.MaskedArray')
        
        #Restructure dataset if structure
        if isStructure :
            dumvalue=value.pop('data')
            if value.has_key('_attributes'):
                for a in value['_attributes'].keys():
                    self.message(4, "copying attribute %s" % a)
                    dumvalue.__setattr__(a,value['_attributes'][a])
            value=copy.deepcopy(dumvalue)
        
        
        curDim, nself=self.get_currentDim()
        
        curInd=np.array(where_list(dimName,curDim[0]))
        curDimVal=np.array(where_list(dimVal,curDim[1]))
        
        existDims= (curInd != -1)
        createDim = (curInd == -1)
        createInd = np.where(createDim)[0]
        
        appendDim=existDims & (curDimVal == -1)
        appendInd=curInd[appendDim]
        
        
#        curInd = set(atools.where_list(dimVal,curDim[1])).intersection(set(atools.where_list(dimName,curDim[0]))) 

        #Get dims to be created
        #######################
        
        

        #Choose case between all different solutions :
        ##############################################
        # 1: create a new variable with at least 1 new dimension
        # 2: extend -> create a new variable using existing dimensions
        # 3: append exisiting variable with data
        # 4: impossible case ?
        
        #1) Create variable
        if createDim.any() & toCreate :           
            #Create Variable
            self.message(4,'Create variable %s '+name)
#            self.__setattr__(name,value)
#            cmd='self.'+name+'=value'

            #Append variable infos to object
            self.par_list=np.append(self.par_list,name)
            dimlist_cp=self.dim_list.tolist()
            dimlist_cp.append(dimName.tolist())
            self.dim_list=np.array(dimlist_cp) #np.append(self.dim_list,dimName.tolist())
        
            updateDim=False
        
        #2) Extend
        elif (not createDim.any()) & toCreate :
            
            #extend variable
            if extend :
                dumvalue = np.ma.masked_array(np.append(np.zeros(curDim[1][curInd]),value.data),mask=np.append(np.ones(curDim[1][curInd],dtype='bool'),value.mask))
                for a in set(value.__dict__.keys()).difference(dumvalue.__dict__.keys()) :
                    dumvalue.__setattr__(a,value.__dict__[a] if hasattr(value, a) else self.__getattribute__(name).__getattribute__(a))
                value=copy.deepcopy(dumvalue)
            
            self.message(4,'Extend variable '+name)
#            self.__setattr__(name,value)
#            cmd='self.'+name+'=value'
#            self.message(4,'exec : '+cmd)

            #Append variable infos to object
            self.par_list=np.append(self.par_list,name)
            dimlist_cp=self.dim_list.tolist()
            dimlist_cp.append(dimName.tolist())
            self.dim_list=np.array(dimlist_cp)
#            self.dim_list=np.append(self.dim_list,dimName)
            
            updateDim=True
        
        #3) Append
        elif (not createDim.any()) & (not toCreate) :
            #append variable
            self.message(4,'Append data to variable '+name)
            
            dumvalue = np.ma.masked_array(np.append(self.__getattribute__(name).data,value.data),mask=np.append(self.__getattribute__(name).mask,value.mask))
            
            #We gather a list of attributes :
            # - already in data structure,
            # - in current data file
            # - and not in output structure
            attributes=set(self.__getattribute__(name).__dict__.keys())
            attributes=attributes.union(value.__dict__.keys())
#             attributes=attributes.difference(self.__getattribute__(name).__dict__.keys())
            attributes=attributes.difference(dumvalue.__dict__.keys())
            
            #Then :
            # - we add attributes of current file not in data structure
            # - we keep attributes of current data structure if they exist 
            for a in attributes :
                dumvalue.__setattr__(a,value.__dict__[a] if hasattr(value, a) else self.__getattribute__(name).__getattribute__(a))
            value=copy.deepcopy(dumvalue)
                    
            updateDim=True
        
        elif createDim.any() & (not toCreate) :
            #Impossible case ?
            self.Error('Impossible case : create dimensions and variable {0} already existing'.format(name))
        
        
        #Append dimensions to variable
        if not dimensions.has_key('_ndims') :
            dumDim=dimStr(dimensions)
            dimensions=dumDim.copy()
        
        #Update variable dimensions
        if updateDim :
            for k in dimensions.keys(): dimensions.update({k:self._dimensions[k]})
        
        value.__setattr__('_dimensions',dimensions)
        
        try : self.__setattr__(name,value)
        except np.ma.core.MaskError : raise 'mask error' 
#           
#        try : exec(cmd)
#        except np.ma.core.MaskError :
#            raise 'mask error' 
#        exec(cmd)
         
        return updateDim