سؤال

هل إعلان الوظيفة هذا في C#:

void foo(string mystring)

نفس هذا في C:

void foo(char *)

أي.في لغة C#، هل تتلقى الوظيفة التي تم استدعاؤها مؤشرًا خلف الكواليس؟

هل كانت مفيدة؟

المحلول

في هذه الحالة المحددة، هو أشبه بما يلي:

void foo(const char *);

سلاسل .Net غير قابلة للتغيير ويتم تمريرها حسب المرجع.ومع ذلك، بشكل عام، تتلقى لغة C# مؤشرًا أو مرجعًا إلى كائن خلف الكواليس.

نصائح أخرى

توجد مؤشرات خلف الكواليس في C#، على الرغم من أنها تشبه المؤشرات الذكية لـ C++، لذلك يتم تغليف المؤشرات الأولية.الحرف* ليس في الواقع نفس System.String نظرًا لأن المؤشر إلى الحرف يعني عادةً بداية مصفوفة أحرف، وسلسلة C# هي كائن ذو حقل طول و مصفوفة أحرف.يشير المؤشر إلى الهيكل الخارجي الذي يشير إلى شيء مثل wchar_t صفيف، لذلك هناك بعض المراوغة مع سلسلة C# وأحرف أوسع لدعم Unicode.

لا.في لغة C# (وجميع لغات .NET الأخرى)، تعد السلسلة نوع بيانات من الدرجة الأولى.إنها ليست مجرد مجموعة من الشخصيات.يمكنك التحويل ذهابًا وإيابًا بينهما، لكنهما لا يتصرفان بنفس الطريقة.هناك عدد من أساليب معالجة السلسلة (مثل "Substring()" و"StartsWith") المتوفرة لفئة String، والتي لا تنطبق على المصفوفات بشكل عام، والتي تكون مصفوفة الأحرف مجرد مثيل لها.

في الأساس، نعم.في C#، السلسلة (في الواقع System.String) هي نوع مرجعي، لذلك عندما يتم استدعاء foo()، فإنها تتلقى مؤشرًا إلى السلسلة في الكومة.

بالنسبة لأنواع القيم (int، double، وما إلى ذلك)، تتلقى الدالة نسخة من القيمة.بالنسبة للكائنات الأخرى، فهو مرجع يشير إلى الكائن الأصلي.

السلاسل خاصة لأنها غير قابلة للتغيير.من الناحية الفنية، يعني ذلك أنها سوف تمر بالمرجع، ولكن من الناحية العملية سوف تتصرف إلى حد كبير مثل نوع القيمة.

يمكنك فرض أنواع القيم لتمرير مرجع باستخدام ref الكلمة الرئيسية:

public void Foo(ref int value) { value = 12 }
public void Bar()
{
    int val = 3;
    Foo(ref val);
    // val == 12
}

لا يوجد في سلسلة C# يونيكود.في C# لا يُسمى مؤشرًا، بل مرجعًا.

إذا كنت تقصد - هل سيتم السماح للطريقة بالوصول إلى محتويات مساحة الأحرف، فالإجابة هي نعم.

نعم، لأن السلسلة ذات حجم ديناميكي، لذلك يجب أن تكون هناك ذاكرة كومة خلف الكواليس

ومع ذلك فهي ليست هي نفسها.

في c يشير المؤشر إلى سلسلة يمكن استخدامها أيضًا في مكان آخر، لذا فإن تغييرها سيؤثر على تلك الأماكن الأخرى.

بقدر ما أعرف، جميع الفئات في C# (لست متأكدًا من الفئات الأخرى) هي أنواع مرجعية.

أي شيء ليس "نوع قيمة"، والذي يغطي بشكل أساسي التعدادات والقيم المنطقية والأنواع الرقمية المضمنة، سيتم تمريره "حسب المرجع"، وهو ما يمكن القول إنه نفس آلية C/C++ للتمرير حسب المرجع أو المؤشر.من الناحية النحوية والدلالية، فهو مطابق بشكل أساسي لتمرير C/C++ حسب المرجع.

ومع ذلك، لاحظ أن السلاسل في C# غير قابلة للتغيير، لذلك على الرغم من تمريرها كمرجع، لا يمكنك تحرير السلسلة دون إنشاء سلسلة جديدة.

لاحظ أيضًا أنه لا يمكنك تمرير وسيطة كـ "const" في C#، بغض النظر عما إذا كان نوع قيمة أو نوع مرجع.

في حين أن هذه هي في الواقع متكافئة بالمعنى الدلالي (أي.الكود يفعل شيئًا باستخدام سلسلة)، C#، مثل Java، يبقي المؤشرات بعيدًا تمامًا عن الاستخدام اليومي، ويحيلها إلى مناطق مثل الانتقالات إلى وظائف نظام التشغيل الأصلية - وحتى في هذه الحالة، هناك فئات إطارية تغلف تلك المؤشرات بشكل جيد، مثل مثل SafeFileHandle.

باختصار، لا تبتعد عن طريقك بالتفكير في المؤشرات في لغة C#.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top