Pengelogan Berparameter
Pemformatan mesej yang cekap
Pengelogan Berparameter ialah pelajaran Java Academy percuma di CoddyKit. Ini ialah pelajaran 3 daripada 4. Anda boleh membaca keseluruhan pelajaran di bawah secara percuma — kemudian berlatih secara praktikal dalam pelayar menggunakan penyunting kod terbina dalam dan tutor kecerdasan buatan 24/7. Pelajaran ini merupakan sebahagian daripada laluan pembelajaran Java Academy, dan kemajuan anda disegerakkan merentas web serta aplikasi CoddyKit. Kursus Java Academy merangkumi sejumlah 4 pelajaran.
Masalah Penggabungan Rentetan
Menggabungkan mesej log membina rentetan penuh sebelum panggilan dibuat, walaupun tahap tersebut dilumpuhkan.
log.debug("id=" + id + " name=" + name) membazirkan CPU apabila DEBUG dimatikan kerana rentetan tetap dibina.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
public static void main(String[] args) {
String name = "Ada"; int id = 7;
// Bad: string is built even if DEBUG is disabled
log.debug("id=" + id + " name=" + name);
}
}Ruang Letak dengan {}
SLF4J menggunakan {} sebagai ruang letak. Hantarkan nilainya sebagai hujah tambahan.
Mesej hanya dibina jika tahap tersebut diaktifkan, jadi kos log yang dilumpuhkan hampir tiada.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
public static void main(String[] args) {
String name = "Ada"; int id = 7;
// Good: no string built unless DEBUG is on
log.debug("id={} name={}", id, name);
}
}Berbilang Ruang Letak
Ruang letak diisi mengikut urutan. {} pertama menerima hujah pertama, yang kedua menerima hujah kedua dan seterusnya.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
public static void main(String[] args) {
log.info("order {} for user {} totaling {} cents", "A-1", 42, 1599);
}
}Mengapa Ia Cekap
Rangka kerja terlebih dahulu menyemak tahap. Jika dilumpuhkan, rangka kerja kembali serta-merta tanpa memanggil toString() pada mana-mana hujah.
Bahagian yang mahal, iaitu pemformatan, berlaku secara tertunda hanya apabila mesej benar-benar akan dikeluarkan.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
static String describe(Object o) { System.out.println("toString called"); return o.toString(); }
public static void main(String[] args) {
// Note: passing describe(...) still evaluates eagerly; pass the raw object instead
log.trace("value={}", new int[]{1, 2, 3});
}
}Hantarkan Objek Mentah, Bukan Rentetan yang Telah Diformat
Untuk mendapatkan manfaat penangguhan, hantarkan objek mentah, bukan panggilan kaedah yang memformatkannya.
Jika Anda menulis log.debug("{}", buildReport()), buildReport() masih dijalankan dengan segera. Hantarkan hujah yang boleh diformatkan sendiri oleh Logger.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
public static void main(String[] args) {
Object user = new Object();
// Logger calls user.toString() only if DEBUG is enabled
log.debug("current user: {}", user);
}
}Pembekal Tertunda untuk Kerja Berat
Apabila pemformatan benar-benar mahal, gunakan API fasih SLF4J 2.x bersama Supplier supaya kerja itu ditangguhkan.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
static String heavyReport() { return "...expensive..."; }
public static void main(String[] args) {
log.atDebug()
.setMessage("report: {}")
.addArgument(() -> heavyReport())
.log();
}
}Meloloskan Kurungan Berlengkung Literal
Jika Anda memerlukan {} literal dalam mesej, meloloskannya dengan garis condong terbalik: \\{}.
Hal ini jarang diperlukan, tetapi berguna apabila mencatat teks seperti JSON.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
public static void main(String[] args) {
// Logs a literal {} then the value
log.info("empty object is \\{} and id is {}", 7);
}
}Pengecualian Bersama Ruang Letak
Anda boleh menggabungkan ruang letak dengan pengecualian pada hujung. SLF4J mengesan bahawa hujah terakhir ialah Throwable dan mencetak jejak tindanannya.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
public static void main(String[] args) {
int id = 99;
try {
throw new RuntimeException("db down");
} catch (Exception e) {
log.error("failed processing record {}", id, e);
}
}
}Elakkan Terlalu Banyak Hujah
Jika bilangan ruang letak dan bilangan hujah tidak sepadan, SLF4J akan melakukan yang terbaik, tetapi hasilnya mungkin kelihatan salah.
Pastikan kedua-duanya sepadan. Untuk lebih daripada beberapa nilai, pertimbangkan konteks berstruktur (MDC).
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
public static void main(String[] args) {
// Two placeholders, two arguments: correct
log.info("user {} did {}", "ada", "login");
}
}Menambah Konteks dengan MDC
Untuk nilai yang dikongsi merentasi banyak baris (seperti id permintaan), letakkannya dalam MDC dan bukannya dalam setiap mesej.
Tataletak corak kemudiannya boleh mencetak nilai MDC pada setiap baris secara automatik.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.slf4j.MDC;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
public static void main(String[] args) {
MDC.put("requestId", "req-1234");
try {
log.info("handling request");
log.info("request done");
} finally {
MDC.clear();
}
}
}Ringkasan Amalan Terbaik
Peraturan untuk pengelogan yang cekap:
- Sentiasa gunakan ruang letak
{}, jangan gunakan penggabungan+. - Hantarkan objek mentah, bukan rentetan yang dibina terlebih dahulu.
- Gunakan pembekal atau
isXEnabled()untuk kerja yang benar-benar berat. - Gunakan MDC untuk konteks rentas fungsi.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
public static void main(String[] args) {
log.info("processed {} items in {} ms", 1000, 42);
}
}Semakan Pantas
Uji pengetahuan Anda tentang pengelogan berparameter.
Imbas Kembali
Anda telah mempelajari pengelogan berparameter:
- Gunakan ruang letak
{}bersama hujah tambahan. - Mesej dibina secara tertunda, hanya apabila tahap tersebut diaktifkan.
- Hantarkan objek mentah; gunakan pembekal untuk kerja berat.
- Gunakan MDC untuk nilai konteks yang dikongsi.
Seterusnya, mengkonfigurasi sistem belakang Logback.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
public static void main(String[] args) {
log.info("Parameterized logging recap: {}", "done");
}
}Pelajari Java dengan tutor kecerdasan buatan — percuma
Tulis dan jalankan kod sebenar dalam pelayar anda, dapatkan bantuan segera daripada tutor kecerdasan buatan yang tersedia 24/7, dan sambung semula dari tempat anda berhenti di web atau dalam aplikasi.
- Kursus
- 104
- Pelajaran
- 374
Soalan Lazim
Adakah pelajaran “Pengelogan Berparameter” percuma?
Ya — teks penuh “Pengelogan Berparameter” boleh dibaca secara percuma di web ini. Untuk berlatih secara interaktif menggunakan penyunting kod terbina dalam dan tutor kecerdasan buatan 24/7, serta membuka kunci baki kursus Java Academy, tingkat taraf kepada CoddyKit PRO. Kursus Java Academy merangkumi sejumlah 4 pelajaran.
Apakah yang akan saya pelajari dalam “Pengelogan Berparameter”?
Pemformatan mesej yang cekap Anda berlatih Java Academy menggunakan kod praktikal yang dijalankan terus dalam pelayar, manakala tutor kecerdasan buatan 24/7 menjawab soalan anda semasa anda mengikuti pelajaran.
Adakah saya memerlukan pengalaman untuk memulakan Java Academy?
Tiada pengalaman terdahulu diperlukan. Pembelajaran Java Academy di CoddyKit disusun untuk pelajar daripada peringkat pemula hingga lanjutan, jadi anda boleh bermula di sini atau dari awal dan belajar mengikut kadar anda sendiri. Ini ialah pelajaran 3 daripada 4.
Berapa lamakah pelajaran “Pengelogan Berparameter” diambil?
Kebanyakan pelajaran CoddyKit mengambil masa kira-kira 5–10 minit. Setiap pelajaran ringkas dan interaktif, jadi anda boleh membuat kemajuan secara berterusan dan menyambung tepat dari tempat anda berhenti di web atau aplikasi.
Bolehkah saya menulis dan menjalankan kod dalam pelajaran Java Academy ini?
Ya. Setiap pelajaran Java Academy menyertakan penyunting kod terbina dalam, jadi anda boleh menulis dan menjalankan kod sebenar terus dalam pelayar serta menerima maklum balas kecerdasan buatan serta-merta — tanpa memerlukan persediaan setempat.
Semua pelajaran dalam kursus ini
- Mengapa Pengelogan Berstruktur
- Fasad SLF4J dan Pengelog
- Pengelogan Berparameter
- Mengkonfigurasi Logback