JavaRush /وبلاگ جاوا /Random-FA /خواندن از صفحه کلید - "خوانندگان"

خواندن از صفحه کلید - "خوانندگان"

در گروه منتشر شد
سلام! در سخنرانی ها و وظایف، ما یاد گرفتیم که چگونه داده ها را به کنسول خروجی دهیم، و بالعکس - خواندن داده ها از صفحه کلید. خواندن از صفحه کلید - "خوانندگان" - 1شما حتی یاد گرفتید که از یک ساختار پیچیده برای این کار استفاده کنید:
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
اما ما هنوز به یک سوال پاسخ نداده ایم.

این حتی چگونه کار می کند؟

در واقع، هر برنامه ای اغلب به تنهایی وجود ندارد. می تواند با سایر برنامه ها، سیستم ها، اینترنت و غیره ارتباط برقرار کند. منظور ما از کلمه "ارتباط" قبل از هر چیز "تبادل داده ها" است. یعنی مقداری داده از بیرون دریافت کنید و برعکس داده های خود را به جایی بفرستید. نمونه های زیادی از تبادل داده بین برنامه ها حتی در زندگی روزمره وجود دارد. بنابراین، در بسیاری از سایت ها، به جای ثبت نام، می توانید با استفاده از حساب فیس بوک یا توییتر خود وارد شوید. در این شرایط، دو برنامه، مثلاً توییتر و سایتی که در آن قصد ثبت نام دارید، داده های لازم را با یکدیگر مبادله می کنند و پس از آن نتیجه نهایی - مجوز موفقیت آمیز را مشاهده می کنید. اصطلاح " جریان " اغلب برای توصیف فرآیند تبادل داده در برنامه نویسی استفاده می شود . اصلا این نام از کجا آمده است؟ "جریان" بیشتر با یک رودخانه یا نهر مرتبط است تا برنامه نویسی. در واقع، این بی دلیل نیست :) یک جریان، در اصل، یک قطعه متحرک از داده است. یعنی در برنامه نویسی این آب نیست که در طول جریان "جریان" می کند، بلکه داده ها به شکل بایت و کاراکتر هستند. از یک جریان داده، می توانیم داده ها را به صورت قسمتی دریافت کنیم و کاری با آن انجام دهیم. مجدداً، بیایید از تشبیه «آب جاری» استفاده کنیم: می‌توانید برای پختن سوپ، خاموش کردن آتش یا آب دادن به گل‌ها، آب را از رودخانه جمع کنید. با استفاده از جریان ها، می توانید با هر منبع داده ای کار کنید: اینترنت، سیستم فایل رایانه خود یا چیز دیگری - مهم نیست. استریم ها ابزاری جهانی هستند. آنها به برنامه اجازه می دهند تا داده ها را از هر جایی دریافت کند (جریان های ورودی) و آن را به هر جایی ارسال کند (جریان های خروجی). وظیفه آنها یکی است - گرفتن داده ها در یک مکان و ارسال آنها به مکان دیگر. جریان ها به دو نوع تقسیم می شوند:
  1. جریان ورودی ( ورودی ) - برای دریافت داده استفاده می شود
  2. جریان خروجی ( خروجی ) - برای ارسال داده ها.
جریان داده های ورودی در جاوا در کلاس InputStreamو جریان داده های خروجی در کلاس پیاده سازی می شود OutputStream. اما راه دیگری برای تقسیم رشته ها وجود دارد. آنها نه تنها به ورودی و خروجی، بلکه به بایت و کاراکتر نیز تقسیم می شوند . در اینجا معنی بدون توضیح واضح است: یک جریان بایت اطلاعات را به صورت مجموعه ای از بایت ها منتقل می کند و یک جریان کاراکتر اطلاعات را به صورت مجموعه ای از کاراکترها منتقل می کند. در این سخنرانی به جزئیات در مورد جریان های ورودی خواهیم پرداخت. و من اطلاعاتی در مورد لینک های خروجی در انتها پیوست خواهم کرد و شما می توانید خودتان در مورد آن بخوانید :) بنابراین، کد ما:
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
احتمالاً هنگام خواندن سخنرانی ها فکر می کردید که بسیار ترسناک به نظر می رسد؟ :) اما این فقط تا زمانی است که بفهمیم این چیز چگونه کار می کند. بیا الان درستش کنیم! بیایید از آخر شروع کنیم. System.inیک شی از کلاس است InputStreamکه در ابتدا در مورد آن صحبت کردیم. این یک جریان ورودی است و به دستگاه ورودی سیستم - صفحه کلید - متصل است. اتفاقا شما به طور غیر مستقیم با او آشنا هستید. از این گذشته ، شما اغلب از "همکار" او در کار خود استفاده می کنید - System.out! System.out- این یک جریان خروجی داده های سیستم است ، برای خروجی به کنسول به روشی System.out.println()که شما دائماً استفاده می کنید استفاده می شود :) System.out- یک جریان برای ارسال داده ها به کنسول و System.in- برای دریافت داده ها از صفحه کلید. ساده است :) علاوه بر این: برای خواندن داده ها از صفحه کلید، می توانیم بدون این ساختار بزرگ انجام دهیم و به سادگی بنویسیم: System.in.read();
public class Main {

   public static void main(String[] args) throws IOException {

       while (true) {
           int x = System.in.read();
           System.out.println(x);
       }
   }
}
در کلاس InputStreamSystem.in، اجازه دهید یادآوری کنم، یک شی از کلاس است InputStream) متدی وجود دارد read()که به شما امکان خواندن داده ها را می دهد. یک مشکل: بایت ها را می خواند نه کاراکترها . بیایید سعی کنیم حرف روسی "Ya" را از صفحه کلید بخوانیم. خروجی کنسول:
Я
208
175
10
حروف روسی 2 بایت در حافظه کامپیوتر اشغال می کنند (بر خلاف حروف انگلیسی که فقط 1 بایت را اشغال می کنند). در این مورد، 3 بایت از جریان خوانده شد: دو بایت اول نشان دهنده حرف "I" ما هستند و دیگری شکست خط (Enter) است. بنابراین، گزینه استفاده از "برهنه" System.inبرای ما مناسب نیست. انسان ها (به استثنای نادر!) نمی توانند بایت ها را بخوانند. اینجاست که کلاس بعدی به کمک ما می آید - InputStreamReader! بیایید بفهمیم این چه نوع حیوانی است.
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(System.in));
جریان را System.inبه InputStreamReader. به طور کلی، اگر نام آن را به روسی ترجمه کنید، همه چیز واضح به نظر می رسد - "خواننده جریان های ورودی". در واقع، دقیقاً برای همین است! ما یک شی کلاس ایجاد می کنیم InputStreamReaderو به آن یک جریان ورودی ارسال می کنیم که باید داده ها را از آن بخواند. در این مورد...
new InputStreamReader(System.in)
ما به آن می گوییم: "شما داده ها را از جریان ورودی سیستم (صفحه کلید) خواهید خواند." اما این تنها عملکرد آن نیست! InputStreamReaderنه تنها داده ها را از جریان دریافت می کند. همچنین جریان های بایت را به جریان های کاراکتری تبدیل می کند . به عبارت دیگر، دیگر لازم نیست نگران ترجمه داده های خوانده شده از زبان «رایانه» به زبان «انسانی» باشید - InputStreamReaderاین کار همه چیز را برای شما انجام خواهد داد. InputStreamReaderالبته، می تواند داده ها را نه تنها از کنسول، بلکه از مکان های دیگر نیز بخواند. به عنوان مثال، از فایل:
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;

public class Main {

   public static void main(String[] args) throws IOException {
       InputStreamReader inputStreamReader = new InputStreamReader(new FileInputStream("C:\\Users\\username\\Desktop\\testFile.txt"));
   }
}
در اینجا یک جریان داده ورودی ایجاد کردیم FileInputStream(این یکی از انواع آن است InputStream)، مسیر فایل را به آن منتقل کردیم و خود جریان را InputStreamReader'y' ارسال کردیم. حالا می‌تواند داده‌های این فایل را بخواند، البته اگر فایل در این مسیر وجود داشته باشد. برای خواندن داده ها (مهم نیست از کجا، از کنسول، یک فایل یا هر جای دیگری)، کلاس InputStreamReaderاز read(). تفاوت بین System.in.read()و چیست InputStreamReader.read()؟ بیایید سعی کنیم همان حرف "I" را با استفاده از InputStreamReader. بگذارید یادآوری کنم، این چیزی است که من فکر کردم System.in.read():
Я
208
175
10
چگونه می تواند همان کار را انجام دهد InputStreamReader؟
public class Main {

   public static void main(String[] args) throws IOException {

       InputStreamReader reader = new InputStreamReader(System.in);
       while (true) {
           int x = reader.read();
           System.out.println(x);
       }
   }
}
خروجی کنسول:
Я
1071
10
تفاوت بلافاصله قابل مشاهده است. آخرین بایت - برای شکست خط - بدون تغییر باقی ماند (عدد 10)، اما حرف خوانده شده "I" به یک کد "1071" تبدیل شد. این خواندن با نمادها است! اگر ناگهان باور نمی کنید که کد 1071 به معنای حرف "I" است، تأیید این موضوع آسان است :)
import java.io.IOException;

public class Main {

   public static void main(String[] args) throws IOException {

       char x = 1071;
       System.out.println(x);
   }
}
خروجی کنسول:

Я
اما اگر InputStreamReaderخیلی خوب است، چرا به موارد بیشتری نیاز دارید BufferedReader؟ InputStreamReaderآیا می توانیم داده ها را بخوانیم و بایت ها را به کاراکتر تبدیل کنیم - چه چیز دیگری نیاز داریم؟ چرا خواننده دیگر؟ :/ پاسخ بسیار ساده است - برای بهره وری بیشتر و راحتی بیشتر . بیایید با عملکرد شروع کنیم. هنگام خواندن داده ها، BufferedReader از یک ناحیه خاص استفاده می کند - یک بافر، که در آن کاراکترهای خوانده شده را "اضافه می کند". در نتیجه زمانی که به این کاراکترها در برنامه نیاز داشته باشیم، از بافر گرفته می شوند و نه مستقیماً از منبع داده (صفحه کلید، فایل و ...) و این باعث صرفه جویی در منابع می شود. برای درک اینکه چگونه این کار می کند، به عنوان مثال، کار یک پیک در یک شرکت بزرگ را تصور کنید. پیک در دفتر می نشیند و منتظر می ماند تا بسته ها را برای او بیاورند. هر بار که او یک بسته جدید دریافت می کند، می تواند بلافاصله به جاده برسد. اما ممکن است در طول روز بسته های زیادی وجود داشته باشد و او مجبور باشد هر بار بین دفتر و آدرس ها رفت و آمد کند. در عوض، پیک جعبه‌ای را در دفتر گذاشت که همه می‌توانستند بسته‌های خود را در آنجا بگذارند. اکنون پیک می تواند با آرامش جعبه را بگیرد و به آدرس ها برود - او در زمان زیادی صرفه جویی می کند، زیرا مجبور نیست هر بار به دفتر بازگردد. کادر در این مثال دقیقاً بافر است و office منبع داده است. برای یک پیک گرفتن نامه از یک صندوق مشترک هنگام تحویل آن بسیار آسان تر از رفتن به دفتر است. همچنین باعث صرفه جویی در مصرف گاز می شود. در یک برنامه هم به همین صورت است - به جای دسترسی هر بار به منبع داده، گرفتن داده ها از بافر به منابع بسیار کمتری نیاز دارد. به همین دلیل BufferedReader+ InputStreamReaderسریعتر از فقط کار می کند InputStreamReader. ما عملکرد را مرتب کردیم، اما در مورد راحتی چطور؟ مزیت اصلی این است که BufferedReaderمی تواند داده ها را نه تنها یک کاراکتر در یک زمان بخواند (البته read()روشی برای این منظور نیز دارد)، بلکه می تواند کل خطوط را نیز بخواند! این کار با استفاده از readLine();
public class Main {

   public static void main(String[] args) throws IOException {

       BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
       String s = reader.readLine();
       System.out.println("We read this line from the keyboard:");
       System.out.println(s);
   }
}
خروجی کنسول:
JavaRush is the best site to learn Java!
Мы считали с клавиатуры эту строку:
JavaRush — лучший сайт для изучения Java!
این به ویژه هنگام خواندن حجم زیادی از داده ها مفید است. هنوز هم می توان یک یا دو خط متن را نویسه به نویسه خواند. اما شمردن یک حرف "جنگ و صلح" تا حدودی مشکل ساز خواهد بود :) حالا کار تاپیک ها برای شما خیلی واضح تر شده است. برای مطالعه بیشتر، در اینجا یک منبع اضافی برای شما آورده شده است: در اینجا می توانید اطلاعات بیشتری در مورد جریان های ورودی و خروجی بخوانید. بررسی ویدئویی BufferedReaderاز یکی از دانش آموزان ما. بله، بله، دانش آموزان ما نه تنها خودشان یاد می گیرند، بلکه فیلم های آموزشی را برای دیگران ضبط می کنند! لایک و عضویت در کانال ما را فراموش نکنید :)
بهتر است از همان ابتدای تحصیل خود را به خواندن اسناد رسمی عادت دهید. این منبع اصلی دانش در مورد زبان است و بیشتر پاسخ ها را همیشه می توان در آنجا یافت.
نظرات
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION