C # जावा सीखने वाले डेवेलपर्स, सबसे बड़े अंतर क्या हैं जिन्हें अनदेखा कर सकते हैं? [बन्द है]


87

C # डेवलपर्स के लिए जो जावा सीखने के लिए घूर रहे हैं, क्या दो भाषाओं के बीच कोई बड़ा अंतर्निहित अंतर है जिसे इंगित किया जाना चाहिए?

हो सकता है कि कुछ लोग चीजों को समान मान लें, लेकिन कुछ ऐसे आयात पहलू हैं जिनकी अनदेखी नहीं की जानी चाहिए? (या आप वास्तव में पेंच कर सकते हैं!)

हो सकता है कि ओओपी निर्माण के संदर्भ में, जीसी के काम करने का तरीका, संदर्भ, तैनाती से संबंधित आदि।




इसके अलावा संभावना अनदेखी हो रहे हैं हमारे अपने "सी # के छुपे हुए सुविधाएँ" stackoverflow.com/questions/9033/hidden-features-of-c
जॉन कश्मीर

जवाबों:


122

मेरे सिर के ऊपर से कुछ गोटेक:

  • जावा में कस्टम मूल्य प्रकार (स्ट्रक्चर्स) नहीं हैं, इसलिए उन्हें ढूंढना परेशान न करें
  • जावा एनम सी # के "नामित संख्या" दृष्टिकोण के लिए बहुत अलग हैं; वे अधिक OO हैं। यदि आप सावधान रहें तो उनका उपयोग बहुत प्रभाव में किया जा सकता है।
  • byte जावा में हस्ताक्षरित है (दुर्भाग्य से)
  • C # में, उदाहरण वैरिएबल इनिशियलाइज़र बेस क्लास कंस्ट्रक्टर के चलने से पहले चलता है; जावा में वे इसके बाद दौड़ते हैं (अर्थात "इस" वर्ग में कंस्ट्रक्टर बॉडी से पहले)
  • C # तरीकों में डिफ़ॉल्ट रूप से सील कर दिया जाता है। जावा में वे डिफ़ॉल्ट रूप से आभासी हैं।
  • C # में डिफ़ॉल्ट एक्सेस संशोधक हमेशा "वर्तमान संदर्भ में उपलब्ध सबसे अधिक प्रतिबंधात्मक पहुंच" है; जावा में यह "पैकेज" एक्सेस है। (यह जावा में विशेष एक्सेस संशोधक पर पढ़ने लायक है।)
  • जावा और सी # में नेस्टेड प्रकार कुछ अलग तरीके से काम करते हैं; विशेष रूप से उनके पास अलग-अलग पहुंच प्रतिबंध हैं, और जब तक आप नेस्टेड प्रकार की घोषणा नहीं करते हैं, तब तक staticइसमें शामिल वर्ग के उदाहरण के लिए एक अंतर्निहित संदर्भ होगा।

5
+1 यह शुरुआत के लिए एक शानदार सूची है।
जिम स्कुबर्ट

3
@ जीन स्कीट: +1, और आप शायद जावा 7 तक लैंबडा और लिनक्यू को मिस करेंगे?
Kb

1
"C # में, उदाहरण वैरिएबल इनिशियलाइज़र बेस क्लास कंस्ट्रक्टर के चलने से पहले चलता है; जावा में वे चलने के बाद चलते हैं (यानी" इस "क्लास" में कंस्ट्रक्टर बॉडी से पहले) - ईयर, क्या आप इसे विस्तृत कर सकते हैं? सुनिश्चित नहीं हैं कि मैं वास्तव में समझते हैं कि आप क्या कह रहे हैं :)
cwap

7
@cwap: C # में, निष्पादन आदेश "उदाहरण चर शुरुआती, बेस क्लास कंस्ट्रक्टर, कंस्ट्रक्टर बॉडी" है। जावा में यह "सुपरक्लास कंस्ट्रक्टर, इंस्टेंस वेरिएबल इनिशियलाइज़र, कंस्ट्रक्टर बॉडी" है। (इंस्टेंस वैरिएबल इनिशियलाइज़र वो होते हैं जो आपको तब मिलते हैं जब आप ऐलान के बिंदु पर एक इंस्टेंस वैरिएबल को वैल्यू असाइन करते हैं।)
जॉन स्कीट

1
@ उत्तर: हां, मेरा यही मतलब है - उत्तरार्द्ध एक वस्तु इनिशियलाइज़र है।
जॉन स्कीट


17

मुझे आश्चर्य है कि किसी ने भी गुणों का उल्लेख नहीं किया है, सी # में काफी मौलिक कुछ है लेकिन जावा में अनुपस्थित है। C # 3 और इसके बाद के संस्करण ने गुणों को स्वचालित रूप से लागू किया है। जावा में आपको गेटएक्स / सेटएक्स प्रकार के तरीकों का उपयोग करना होगा।

एक और स्पष्ट अंतर LINQ और लैम्ब्डा एक्सप्रेशन हैं जावा में C # 3 अनुपस्थित हैं।

जावा से कुछ अन्य सरल लेकिन उपयोगी चीजें गायब हैं जैसे वर्बटीम स्ट्रिंग्स (@ ""), ऑपरेटर ओवरलोडिंग, उपज का उपयोग करने वाले पुनरावृत्त और पूर्व प्रोसेसर जावा में भी गायब हैं।

C # में मेरा व्यक्तिगत पसंदीदा नाम है कि नाम स्थान के भौतिक निर्देशिका संरचना का पालन नहीं करना है। मुझे वास्तव में यह लचीलापन पसंद है।


10

बहुत सारे अंतर हैं, लेकिन ये मेरे लिए दिमाग में आते हैं:

  • जावा में ऑपरेटर ओवरलोडिंग का अभाव। अपनी आवृत्ति देखें। उदाहरण (उदाहरण 2) बनाम उदाहरण == उदाहरण 2 (विशेषकर w / स्ट्रिंग्स)।
  • एक I के साथ पूर्वनिर्मित नहीं होने वाले इंटरफेस का उपयोग करें। अक्सर आप इसके स्थान पर Impl के साथ प्रत्यय या नाम स्थान देखते हैं।
  • जावा मेमोरी मॉडल के कारण डबल चेक किया गया लॉकिंग काम नहीं करता है।
  • आप उन्हें कक्षा के नाम के साथ उपसर्ग किए बिना स्थिर विधियों का आयात कर सकते हैं, जो कुछ मामलों (डीएसएल) में बहुत उपयोगी है।
  • जावा में स्विच स्टेटमेंट को डिफ़ॉल्ट की आवश्यकता नहीं होती है, और आप केस लेबल (IIRC) के रूप में स्ट्रिंग्स का उपयोग नहीं कर सकते।
  • जावा जेनरिक आपको गुस्सा दिलाएगा। जावा जेनरिक रनटाइम में मौजूद नहीं है (कम से कम 1.5 में), वे एक कंपाइलर ट्रिक हैं, जो यदि आप जेनेरिक प्रकारों पर प्रतिबिंब बनाना चाहते हैं तो समस्याएँ पैदा करती हैं।

4
अंतिम बार मैंने जाँच की थी, स्ट्रिंग्स ने अधिभार == नहीं दिया था, और मैंने इसे जावा 7 के लिए भी नहीं जोड़ा है। हालांकि, वे स्ट्रिंग समवर्ती के लिए अधिभार + करते हैं।
माइकल मैडसेन

3
हां, == के साथ तार की तुलना करना newbies के लिए एक बहुत ही सामान्य नुकसान है। .equalsवह है जो आपको उपयोग करना है।
माइकल मायर्स

इसके अलावा, मैं स्थैतिक तरीकों के बारे में टिप्पणी को नहीं समझता। बहुत अधिक सभी भाषाएँ स्थिर विधियों या समकक्ष की अनुमति नहीं देती हैं?
माइकल मायर्स

मैंने लगभग इसे अपडाउन किया, लेकिन मैं जेनरिक के बारे में असहमत हूं। मुझे इरेज़र टाइप पसंद है।
फिन

2
"जावा में स्विच स्टेटमेंट को डिफ़ॉल्ट की आवश्यकता नहीं है" - और न ही सी #।
RenniePet

8

.NET ने जेनेरिक को फिर से परिभाषित किया है; जावा ने जेनेरिक को मिटा दिया है।

अंतर यह है: यदि आपके पास कोई ArrayList<String>ऑब्जेक्ट है, तो .NET में, आप बता सकते हैं (रनटाइम पर) कि ऑब्जेक्ट में टाइप है ArrayList<String>, जबकि जावा में, रनटाइम में, ऑब्जेक्ट टाइप का है ArrayList; Stringहिस्सा खो दिया है। यदि आप गैर- Stringवस्तुओं में डालते हैं ArrayList, तो सिस्टम इसे लागू नहीं कर सकता है, और आप आइटम को बाहर निकालने की कोशिश करने के बाद ही इसके बारे में जान पाएंगे, और कलाकार विफल हो जाता है।


1
... हालाँकि यह जोड़ने योग्य है कि आप Stringउस सूची में गैर- ऑब्जेक्ट नहीं डाल सकते हैं, बिना अनियंत्रित डाली, कहीं , और संकलक आपको सही ढंग से उस बिंदु पर चेतावनी देगा कि संकलक अब सामान्य सीमा की जांच नहीं कर सकता है। जब तक आपकी सूची को हमेशा एक चर में संग्रहित किया जाता है, तब तक List<String>इसमें गैर-स्ट्रिंग ऑब्जेक्ट डालने का प्रयास नहीं होगा।
एंड्रीज डॉयल

"गैर-स्ट्रिंग ऑब्जेक्ट्स ArrayList में, सिस्टम इसे लागू नहीं कर सकता है": ध्यान दें कि सिस्टम इसे संकलन-समय पर लागू करता है । हालांकि आप इसे कास्टिंग द्वारा (या जेनरिक का उपयोग नहीं कर) कर सकते हैं; तब रनटाइम चेक इसे पकड़ लेगा, लेकिन केवल निकालने के दौरान।
सालेके

1
@Andrzej, @ स्लेसके: मैं केवल रनटाइम के बारे में बात कर रहा हूं। कहते हैं कि आप प्रतिबिंब के माध्यम से वस्तु प्राप्त करते हैं, और इसकी addविधि (फिर से, प्रतिबिंब के माध्यम से) को लागू करते हैं। क्या सिस्टम Stringसीधे गैर- ऑब्जेक्ट को अस्वीकार कर देगा , या केवल परिणाम डालते समय get?
क्रिस जेस्टर-यंग

@ स्लेस्क: लेकिन IIRC आपको केवल टाइप चेक को दरकिनार करने के लिए एक निहित कास्ट की आवश्यकता है।
निकी

@ जूदाः मैंने आपका परिवर्तन वापस कर दिया (हां, इस तथ्य के एक साल बाद), क्योंकि आपके पास प्रकार की वस्तुएं नहीं हो सकती हैं List। आपके पास List, जैसे ArrayListऔर से उतरने वाली वस्तुएं हो सकती हैं LinkedList। ( जब वे चारों ओर से गुजर रहे हों, तो इसका उपयोग Listकरना महत्वपूर्ण है ArrayList, लेकिन यह इस तथ्य को नहीं बदलता है जो आप नहीं कह सकते new List()।)
क्रिस जस्टर-यंग

6

जावा से C # में एक चीज मुझे याद है, जाँच किए गए अपवादों की मजबूर हैंडलिंग। C # में यह आम बात है कि कोई एक अपवाद से अनभिज्ञ हो जिसे कोई विधि फेंक सकती है और आप उन्हें खोजने के लिए दस्तावेज़ीकरण या परीक्षण की दया पर हैं। चेक अपवादों के साथ जावा में ऐसा नहीं है।


1
FWIW, इसे C # के डिबेट में माना जाता था और इन्हें छोड़ने का औचित्य वास्तविक है। Artima.com/intv/handcuffs.html पर विचार करें । ऐसा नहीं है कि डिज़ाइनर अपवाद रूप से जाँच किए गए अपवादों के विरोधी हैं - बल्कि, वे एक बेहतर तकनीक की प्रतीक्षा कर रहे हैं जो सभी बालों की कमियों के बिना समान लाभ प्रदान करती है।
ग्रेग डी

हाँ, हाँ, एक बहुत ही विवादास्पद विषय ...
sleske

2
मुझे यह तथ्य पसंद है कि C # में अपवादों की जाँच नहीं है, लेकिन यह अंतर को इंगित करने वाला पहला पोस्ट था, इसलिए +1।
निक

5

जावा में मूल्य प्रकारों के बजाय आदिम के लिए ऑटोबॉक्सिंग है, इसलिए हालांकि System.Int32[]सी # में मूल्यों Integer[]की एक सरणी है Integer, वस्तुओं के संदर्भों की एक सरणी है , और जैसे कि उच्च प्रदर्शन गणना के लिए उपयुक्त नहीं है।


1
पीट: यह एक उत्कृष्ट बिंदु है, और एक जिसे मैं कभी नहीं जानता था या कम से कम कभी नहीं माना जाता था (एक सी # डेवलपर और जावा के लिए नया)।
जिम स्कुबर्ट

4

कोई प्रतिनिधि या ईवेंट नहीं - आपको इंटरफेस का उपयोग करना होगा। सौभाग्य से, आप कक्षाएं और इंटरफ़ेस कार्यान्वयन इनलाइन बना सकते हैं, इसलिए यह इतना बड़ा सौदा नहीं है


3
"इतनी बड़ी बात नहीं है"। सही। क्योंकि x => x.Fooबनाम new Bar() { public void M(SomeType x) { return x.Foo; } }- कौन परवाह करता है कि कोड 10 गुना कम है?
Kirk Woll

2

जावा में अंतर्निहित तिथि / कैलेंडर कार्यक्षमता System.DateTime की तुलना में भयानक है। यहाँ इसके बारे में बहुत सी जानकारी है: जावा तिथि और समय एपीआई के साथ क्या गलत है?

इनमें से कुछ सी # डेवलपर के लिए मिल सकते हैं:

  • जावा तिथि वर्ग परिवर्तनशील है जो खतरनाक के चारों ओर लौटने और गुजरने की तारीख बना सकता है।
  • अधिकांश java.util.Date कंस्ट्रक्टरों को पदावनत किया जाता है। बस एक तारीख को तत्काल क्रिया करना बहुत क्रिया है।
  • मैंने java.util.Date क्लास को वेब सर्विसेज के साथ अच्छी तरह से इंटरप्ट करने के लिए कभी नहीं लिया है। ज्यादातर मामलों में दोनों तरफ की तारीखें बेतहाशा किसी और तारीख और समय में तब्दील हो गईं।

इसके अतिरिक्त, जावा में सभी समान सुविधाएँ नहीं हैं जो GAC और दृढ़ता से नामित असेंबली लाती हैं। जार नर्क बाहरी पुस्तकालयों को जोड़ने / संदर्भित करने पर क्या गलत हो सकता है के लिए शब्द है।

जहां तक ​​पैकेजिंग / तैनाती का सवाल है:

  • ईएआर / डब्ल्यूएआर प्रारूप में वेब अनुप्रयोगों को पैकेज करना मुश्किल हो सकता है जो वास्तव में कई अलग-अलग एप्लिकेशन सर्वरों में स्थापित होते हैं और चलते हैं (ग्लासफिश, वेबस्पेयर, आदि)।
  • Windows सेवा के रूप में अपने जावा ऐप को तैनात करना C # की तुलना में बहुत अधिक प्रयास करता है। इसके लिए मुझे जो भी सिफारिशें मिलीं उनमें से अधिकांश में एक गैर-मुक्त 3 पार्टी पुस्तकालय शामिल था
  • एप्लिकेशन कॉन्फ़िगरेशन लगभग उतना आसान नहीं है जितना कि आपके प्रोजेक्ट में एक app.config फ़ाइल शामिल है। एक java.util.Properties वर्ग है, लेकिन यह उतना मजबूत नहीं है और आपको .properties फ़ाइल को ड्रॉप करने के लिए सही जगह मिल सकती है।

1

जावा में कोई प्रतिनिधि नहीं हैं। इसलिए, उन सभी लाभों से अलग, जो प्रतिनिधि तालिका में लाते हैं, घटनाएं अलग तरह से भी काम करती हैं। केवल एक विधि को हुक करने के बजाय, आपको एक इंटरफ़ेस लागू करने और इसके बजाय संलग्न करने की आवश्यकता है।


1

एक बात जो मेरी साक्षात्कार सूची में b / c से मिलती है, वह यह है कि विधि छिपाने के लिए जावा में कोई "नया" कीवर्ड एनालॉग नहीं है और कोई संकलक चेतावनी नहीं है "आपको यहां नया डाल देना चाहिए"। जब आप ओवरराइड करने का मतलब छिपाते हैं तो आकस्मिक विधि बग्स की ओर ले जाती है।

(उदाहरण के लिए संपादित करें) उदाहरण, B, A से प्राप्त होता है (C # सिंटैक्स का उपयोग करके, जावा ने पिछली बार मेरे द्वारा जांचे गए तरीके से ही व्यवहार किया है लेकिन संकलक चेतावनी का उत्सर्जन नहीं करता है)। क्या A के फू को बुलाया जाता है, या B का फू? (ए को बुलाया जाता है, संभवतः बी को लागू करने वाले देव को आश्चर्यचकित करता है)।

class A 
{
public void foo() {code}
}

class B:A
{
public void foo() {code}
}    

void SomeMethod()
{
A a = new B(); // variable's type is declared as A, but assigned to an object of B.
a.foo();
}

2
कैसे आप गलती से जावा में एक इंस्टेंस विधि छिपाते हैं? वे या तो अंतिम हैं - इसलिए newजानबूझकर छिपाने के लिए कोई ओवरराइड या विधि नहीं है - या गैर-अंतिम इसलिए छिपाए जाने के बजाय ओवरराइड किया गया है।
पीट किर्कम

जोड़ा गया उदाहरण। मैंने कुछ समय में जावा में इसका परीक्षण नहीं किया है, लेकिन साक्षात्कार का प्रश्न मूल रूप से मेरी पिछली कंपनी के जावा समूह से आया है। सी # में, आमतौर पर संकलक चेतावनी का मतलब है कि लोग नाम बदलते हैं। मैं मानता हूं कि यह बहुत अजीब मामला है, लेकिन ओपी ऐसी चीजों के लिए पूछ रहा था जो लैंग्स को स्विच करते समय समस्याओं को खोजने के लिए संभावित रूप से कठिन होगा।
जिम एल

1
यहाँ अंतर यह है कि जावा में सभी विधियाँ आभासी हैं (इसलिए जावा में, यह B.foo () कहलाएगा क्योंकि जावा हमेशा गतिशील विधि प्रेषण करता है), जबकि C # विधियों में डिफ़ॉल्ट रूप से आभासी नहीं होते हैं (और A.foo) () कहा जाएगा)। जावा के लिए कई कोडिंग स्टाइल चेकर्स आपको बताएंगे कि बी को @ ऑवरराइड एनोटेशन का उपयोग करना चाहिए।
विलियम बिलिंग्सले 3

1

Java में LINQ नहीं है और प्रलेखन नरक है। जावा में उपयोगकर्ता इंटरफेस विकसित करने के लिए एक दर्द है, आप Microsoft द्वारा हमें दी गई सभी अच्छी चीजें खो देते हैं (WPF, WCF, आदि ...) लेकिन मुश्किल से उपयोग किया जाता है, "एपीआई" का दस्तावेज।


0

जब मैं C # से आने वाले जावा के साथ काम कर रहा हूं, तब तक जो एक मुद्दा है, वह अपवाद है और त्रुटियां अलग हैं।

उदाहरण के लिए आप कैच (अपवाद ई) का उपयोग करके मेमोरी एरर को नहीं पकड़ सकते।

अधिक जानकारी के लिए निम्नलिखित देखें:

क्यों-है-जावा-lang-OutOfMemoryError-जावा-ढेर अंतरिक्ष-नहीं पकड़ा


यह जानबूझकर कि जिस तरह से यह पकड़ने से आवेदन प्रोग्रामर को हतोत्साहित करने के लिए डिज़ाइन किया गया है
finnw

हाँ, मुझे यकीन है कि यह था, लेकिन सी # की तरफ से आ रहा है, जहाँ आप सभी को चिंता करने की ज़रूरत है, अपवादों को पकड़ना है, मुझे एक पाश के लिए फेंक दिया :)
क्रिस Persichetti

0

जब से मैं जावा में आया हूं तब से यह बहुत लंबा है, लेकिन जिन चीजों को मैंने एप्लिकेशन डेवलपमेंट में बल्ले से देखा है, वे C # ईवेंट मॉडल, C # ड्रैग और ड्रॉप vs स्विंग में लेआउट मैनेजर्स का उपयोग कर रहे हैं (यदि आपका ऐप देव कर रहा है), और अपवाद हैंडलिंग जावा यह सुनिश्चित करता है कि आप एक अपवाद को पकड़ते हैं और C # की आवश्यकता नहीं है।


0

आपके शीर्षक में आपके बहुत सीधे सवाल के जवाब में:

"C # जावा सीखने वाले डेवेलपर्स, सबसे बड़े अंतर क्या हैं जिन्हें अनदेखा कर सकते हैं?"

एक: तथ्य यह है कि जावा विंडोज पर काफी धीमी है।


4
मैं OpenSuSE 64 बिट और विंडोज 7 64 बिट चलाता हूं, और विंडोज में ग्रहण आईडीई ("लगता है") तेज है। क्या आपका जवाब व्यक्तिगत अवलोकन या वास्तविक बेंचमार्क पर आधारित है?
जिम शुबर्ट

0

जब मुझे जावा पर स्विच करने में सबसे ज्यादा फर्क पड़ता है तो वह है स्ट्रिंग डिक्लेरेशन।

stringजावा में C # (अधिकांश समय)String

यह बहुत आसान है, लेकिन मुझ पर विश्वास करो, यह आपको इतना समय खो देता है जब आपको आदत sनहीं है S!

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.