Recherche…


Remarques

  • Pour pouvoir utiliser le mot clé unsafe dans un projet .Net, vous devez cocher "Autoriser le code non sécurisé" dans Propriétés du projet => Créer
  • L'utilisation d'un code non sécurisé peut améliorer les performances, mais au détriment de la sécurité du code (d'où le terme unsafe ).

Par exemple, lorsque vous utilisez une boucle for, un tableau comme celui-ci:

for (int i = 0; i < array.Length; i++)
{
    array[i] = 0;
}

.NET Framework garantit que vous ne dépassez pas les limites du tableau, en lançant une IndexOutOfRangeException si l'index dépasse les limites.

Toutefois, si vous utilisez un code non sécurisé, vous pouvez dépasser les limites du tableau comme suit:

unsafe
{
    fixed (int* ptr = array)
    {
        for (int i = 0; i <= array.Length; i++)
        {
            *(ptr+i) = 0;
        }
    }
}

Index de tableau dangereux

void Main()
{
    unsafe
    {
        int[] a = {1, 2, 3};
        fixed(int* b = a)
        {
            Console.WriteLine(b[4]);
        }
    }
}

L'exécution de ce code crée un tableau de longueur 3, mais essaie ensuite d'obtenir le 5ème élément (index 4). Sur ma machine, cette 1910457872 imprimée, mais le comportement n'est pas défini.

Sans le bloc unsafe , vous ne pouvez pas utiliser de pointeurs et par conséquent, vous ne pouvez pas accéder aux valeurs après la fin d'un tableau sans provoquer une exception.

Utiliser des tableaux non sécurisés

Lors de l'accès aux tableaux avec des pointeurs, il n'y a pas de vérification des limites et par conséquent, aucune IndexOutOfRangeException ne sera lancée. Cela rend le code plus rapide.

Affectation de valeurs à un tableau avec un pointeur:

class Program
{
    static void Main(string[] args)
    {
        unsafe
        {
            int[] array = new int[1000]; 
            fixed (int* ptr = array)
            {
                for (int i = 0; i < array.Length; i++)
                {
                    *(ptr+i) = i; //assigning the value with the pointer
                }
            }
        }
    }
}

Alors que la contrepartie sûre et normale serait:

class Program
{
    static void Main(string[] args)
    {            
        int[] array = new int[1000]; 

        for (int i = 0; i < array.Length; i++)
        {
            array[i] = i;
        }
    }
}

La partie dangereuse sera généralement plus rapide et la différence de performance peut varier en fonction de la complexité des éléments de la matrice et de la logique appliquée à chacun. Même s'il peut être plus rapide, il doit être utilisé avec précaution, car il est plus difficile à entretenir et plus facile à briser.

Utilisation de unsafe avec des chaînes

var s = "Hello";      // The string referenced by variable 's' is normally immutable, but
                      // since it is memory, we could change it if we can access it in an 
                      // unsafe way.

unsafe                // allows writing to memory; methods on System.String don't allow this
{
  fixed (char* c = s) // get pointer to string originally stored in read only memory
    for (int i = 0; i < s.Length; i++)
      c[i] = 'a';     // change data in memory allocated for original string "Hello"
}
Console.WriteLine(s); // The variable 's' still refers to the same System.String
                      // value in memory, but the contents at that location were 
                      // changed by the unsafe write above.
                      // Displays: "aaaaa"


Modified text is an extract of the original Stack Overflow Documentation
Sous licence CC BY-SA 3.0
Non affilié à Stack Overflow