Variables

متغير، في جوليا، هو اسم مرتبط (أو مقيد) بقيمة. إنه مفيد عندما تريد تخزين قيمة (التي حصلت عليها بعد بعض الرياضيات، على سبيل المثال) للاستخدام لاحقًا. على سبيل المثال:

# Assign the value 10 to the variable x
julia> x = 10
10

# Doing math with x's value
julia> x + 1
11

# Reassign x's value
julia> x = 1 + 1
2

# You can assign values of other types, like strings of text
julia> x = "Hello World!"
"Hello World!"

تقدم جوليا نظامًا مرنًا للغاية لتسمية المتغيرات. أسماء المتغيرات حساسة لحالة الأحرف، وليس لها معنى دلالي (أي أن اللغة لن تعالج المتغيرات بشكل مختلف بناءً على أسمائها).

julia> x = 1.0
1.0

julia> y = -3
-3

julia> Z = "My string"
"My string"

julia> customary_phrase = "Hello world!"
"Hello world!"

julia> UniversalDeclarationOfHumanRightsStart = "人人生而自由,在尊严和权利上一律平等。"
"人人生而自由,在尊严和权利上一律平等。"

أسماء يونيكود (بتشفير UTF-8) مسموح بها:

julia> δ = 0.00001
1.0e-5

julia> 안녕하세요 = "Hello"
"Hello"

في REPL الخاص بـ Julia والعديد من بيئات تحرير Julia الأخرى، يمكنك كتابة العديد من رموز الرياضيات اليونيكود عن طريق كتابة اسم الرمز LaTeX مع شرطة مائلة متبوعة بمفتاح التبويب. على سبيل المثال، يمكن إدخال اسم المتغير δ عن طريق كتابة \delta-tab، أو حتى α̂⁽²⁾ عن طريق \alpha-tab-\hat-tab-\^(2)-tab. (إذا وجدت رمزًا في مكان ما، على سبيل المثال في كود شخص آخر، ولا تعرف كيفية كتابته، فإن مساعدة REPL ستخبرك: فقط اكتب ? ثم الصق الرمز.)

جوليا ستسمح لك حتى بتظليل الثوابت والدوال المصدرة الموجودة بدوال محلية (على الرغم من أن ذلك غير موصى به لتجنب الارتباك المحتمل):

julia> pi = 3
3

julia> pi
3

julia> sqrt = 4
4

julia> length() = 5
length (generic function with 1 method)

julia> Base.length
length (generic function with 79 methods)

ومع ذلك، إذا حاولت إعادة تعريف ثابت أو دالة مدمجة قيد الاستخدام بالفعل، ستعطيك جوليا خطأ:

julia> pi
π = 3.1415926535897...

julia> pi = 3
ERROR: cannot assign a value to imported variable Base.pi from module Main

julia> sqrt(100)
10.0

julia> sqrt = 4
ERROR: cannot assign a value to imported variable Base.sqrt from module Main

Allowed Variable Names

يجب أن تبدأ أسماء المتغيرات بحرف (A-Z أو a-z) أو شرطة سفلية، أو مجموعة من نقاط الشيفرة Unicode التي تزيد عن 00A0؛ على وجه الخصوص، Unicode character categories Lu/Ll/Lt/Lm/Lo/Nl (الحروف)، Sc/So (العملات ورموز أخرى)، وبعض الشخصيات الشبيهة بالحروف الأخرى (مثل مجموعة من رموز الرياضيات Sm) مسموح بها. يمكن أن تتضمن الأحرف اللاحقة أيضًا ! والأرقام (0-9 وأحرف أخرى في الفئات Nd/No)، بالإضافة إلى نقاط الشيفرة Unicode الأخرى: الحركات وعلامات التعديل الأخرى (الفئات Mn/Mc/Me/Sk)، وبعض موصلات الترقيم (الفئة Pc)، والرموز، وبعض الشخصيات الأخرى.

تعتبر العوامل مثل + معرفات صالحة أيضًا، ولكن يتم تحليلها بشكل خاص. في بعض السياقات، يمكن استخدام العوامل تمامًا مثل المتغيرات؛ على سبيل المثال، (+) تشير إلى دالة الجمع، و(+) = f ستعيد تعيينها. يتم تحليل معظم عوامل Unicode infix (في فئة Sm)، مثل ، كعوامل infix وهي متاحة للطرق المعرفة من قبل المستخدم (على سبيل المثال، يمكنك استخدام const ⊗ = kron لتعريف كمنتج كرونكر infix). يمكن أيضًا إضافة علامات تعديل، أو علامات تمييز، أو تحت/فوق الكتابة إلى العوامل، على سبيل المثال، +̂ₐ″ يتم تحليله كعامل infix بنفس أولوية +. هناك حاجة إلى مسافة بين عامل ينتهي بحرف تحت/فوق الكتابة واسم متغير لاحق. على سبيل المثال، إذا كان +ᵃ عاملًا، فإن +ᵃx يجب أن تُكتب كـ +ᵃ x لتمييزها عن + ᵃx حيث أن ᵃx هو اسم المتغير.

فئة معينة من أسماء المتغيرات هي تلك التي تحتوي فقط على شرطات سفلية. هذه المعرفات هي للكتابة فقط. أي أنه يمكن فقط تعيين قيم لها، والتي يتم التخلص منها على الفور، ولا يمكن استخدام قيمها بأي شكل من الأشكال.

julia> x, ___ = size([2 2; 1 1])
(2, 2)

julia> y = ___
ERROR: syntax: all-underscore identifiers are write-only and their values cannot be used in expressions

julia> println(___)
ERROR: syntax: all-underscore identifiers are write-only and their values cannot be used in expressions

The only explicitly disallowed names for variables are the names of the built-in Keywords:

julia> else = false
ERROR: syntax: unexpected "else"

julia> try = "No"
ERROR: syntax: unexpected "="

تعتبر بعض أحرف يونيكود متكافئة في المعرفات. يتم التعامل مع طرق مختلفة لإدخال أحرف يونيكود المدمجة (مثل، الحروف المشددة) على أنها متكافئة (على وجه التحديد، معرفات جوليا هي NFC. تشمل جوليا أيضًا بعض المعادلات غير القياسية للأحرف التي تشبه بصريًا والتي يمكن إدخالها بسهولة بواسطة بعض طرق الإدخال. يتم التعامل مع أحرف يونيكود ɛ (U+025B: حرف اللاتيني الصغير المفتوح e) و µ (U+00B5: علامة الميكرو) على أنها متكافئة مع الحروف اليونانية المقابلة. يتم التعامل مع النقطة الوسطى · (U+00B7) و interpunct اليونانية · (U+0387) على أنها مشغل النقطة الرياضية (U+22C5). يتم التعامل مع علامة الطرح (U+2212) على أنها متكافئة مع علامة الهايفن-ناقص - (U+002D).

Assignment expressions and assignment versus mutation

تقوم عملية الإسناد variable = value بـ "ربط" الاسم variable بالقيمة value المحسوبة على الجانب الأيمن، ويتم التعامل مع عملية الإسناد بالكامل من قبل جوليا كتعبيير يساوي القيمة value على الجانب الأيمن. هذا يعني أن عمليات الإسناد يمكن أن تكون متسلسلة (نفس value تُعطى لعدة متغيرات مع variable1 = variable2 = value) أو تُستخدم في تعبيرات أخرى، وهذا هو السبب أيضًا في أن نتيجتها تُعرض في REPL كقيمة الجانب الأيمن. (بشكل عام، يعرض REPL قيمة أي تعبير تقوم بتقييمه.) على سبيل المثال، هنا تُستخدم القيمة 4 من b = 2+2 في عملية حسابية أخرى وإسناد:

julia> a = (b = 2+2) + 3
7

julia> a
7

julia> b
4

الارتباك الشائع هو التمييز بين التعيين (إعطاء "اسم" جديد لقيمة) و التحوير (تغيير قيمة). إذا قمت بتشغيل a = 2 تليها a = 3، فقد قمت بتغيير "الاسم" a للإشارة إلى قيمة جديدة 3 ... لم تقم بتغيير الرقم 2، لذا فإن 2+2 سيظل يعطي 4 وليس 6! يصبح هذا التمييز أكثر وضوحًا عند التعامل مع أنواع قابلة للتغيير مثل arrays، التي يمكن تغيير محتوياتها:

julia> a = [1,2,3] # an array of 3 integers
3-element Vector{Int64}:
 1
 2
 3

julia> b = a   # both b and a are names for the same array!
3-element Vector{Int64}:
 1
 2
 3

هنا، السطر b = a لا يعمل على إنشاء نسخة من المصفوفة a، بل ببساطة يربط الاسم b بنفس المصفوفة a: كلا من b و a "يشيران" إلى مصفوفة واحدة [1,2,3] في الذاكرة. على النقيض من ذلك، فإن تعيين a[i] = value يغير محتويات المصفوفة، وستكون المصفوفة المعدلة مرئية من خلال كلا الاسمين a و b:

julia> a[1] = 42     # change the first element
42

julia> a = 3.14159   # a is now the name of a different object
3.14159

julia> b   # b refers to the original array object, which has been mutated
3-element Vector{Int64}:
 42
  2
  3

هذا يعني أن a[i] = value (اسم مستعار لـ setindex!) يعدل كائن مصفوفة موجود في الذاكرة، يمكن الوصول إليه عبر a أو b. بعد ذلك، فإن تعيين a = 3.14159 لا يغير هذه المصفوفة، بل يربط ببساطة a بكائن مختلف؛ لا تزال المصفوفة قابلة للوصول عبر b. صيغة شائعة أخرى لتعديل كائن موجود هي a.field = value (اسم مستعار لـ setproperty!)، والتي يمكن استخدامها لتغيير mutable struct. هناك أيضًا تعديل عبر تعيين النقطة، على سبيل المثال b .= 5:7 (الذي يعدل مصفوفتنا b في المكان لتحتوي على [5,6,7])، كجزء من vectorized "dot" syntax في جوليا.

عندما تستدعي function في جوليا، فإنه يتصرف كما لو كنت تعيّن قيم الوسائط إلى أسماء متغيرات جديدة تتوافق مع وسائط الدالة، كما تم مناقشته في Argument-Passing Behavior. (بواسطة convention، فإن الدوال التي تعدل واحدًا أو أكثر من وسائطها تحمل أسماء تنتهي بـ !.)

Stylistic Conventions

بينما تفرض جوليا قيودًا قليلة على الأسماء الصالحة، فقد أصبح من المفيد اعتماد الاتفاقيات التالية:

  • أسماء المتغيرات تكون بحروف صغيرة.
  • يمكن الإشارة إلى فصل الكلمات بواسطة الشرطات السفلية ('_')، ولكن يُنصح بتجنب استخدام الشرطات السفلية ما لم يكن الاسم سيكون من الصعب قراءته بخلاف ذلك.
  • تبدأ أسماء Types و Modules بحرف كبير ويتم إظهار فصل الكلمات باستخدام أسلوب الكتابة العلوية بدلاً من الشرطات السفلية.
  • أسماء functions و macros تكون بحروف صغيرة، بدون شرطات سفلية.
  • تقوم الدوال التي تكتب إلى معطياتها بإنهاء أسمائها بـ !. تُسمى هذه أحيانًا "دوال متغيرة" أو "دوال في المكان" لأنها تهدف إلى إحداث تغييرات في معطياتها بعد استدعاء الدالة، وليس فقط إرجاع قيمة.

لمزيد من المعلومات حول الاتفاقيات الأسلوبية، راجع Style Guide.