Item Bank (Tapşırıq Bankı) CAT sisteminin ürəyidir. Keyfiyyətli və yaxşı strukturlaşdırılmış tapşırıq bankı CAT-ın effektivliyini, etibarlılığını və ədalətliliyini təmin edir. Bu bölmədə kompleks tapşırıq bankının necə yaradılacağını və idarə ediləcəyini öyrənəcəksiniz.
Tapşırıq bankı sadəcə tapşırıqların məcmusundan daha çox şeydir - bu, stratejik olaraq dizayn edilmiş, çoxölçülü məzmun strukturu və psixometrik xüsusiyyətlərə malik sistem komponentdir.
Keyfiyyətli tapşırıq bankı aşağıdakı prinsiplərə əsaslanır:
# Bank dizayn prinsiplərini demonstrasiya edək
demonstrate_bank_principles <- function() {
cat("=== TAPŞIRIQ BANKI DİZAYN PRİNSİPLƏRİ ===\n\n")
# İdeal bank ölçüsü hesablaması
max_test_length <- 30
target_exposure_rate <- 0.20 # Hər tapşırığın istifadə tezliyi
recommended_bank_size <- ceiling(max_test_length / target_exposure_rate)
cat("1. BANK ÖLÇÜsÜ HESABLAMASi:\n")
cat(" Maksimum test uzunluğu:", max_test_length, "tapşırıq\n")
cat(" Hədəf exposure nisbəti:", target_exposure_rate, "\n")
cat(" Tövsiyə edilən bank ölçüsü:", recommended_bank_size, "tapşırıq\n\n")
# Çətinlik paylanması
cat("2. ÇƏTİNLİK PAYLANMASI STRATEGİYASI:\n")
difficulty_categories <- c("Çox asan", "Asan", "Orta-asan", "Orta",
"Orta-çətin", "Çətin", "Çox çətin")
recommended_percentages <- c(10, 15, 20, 20, 20, 10, 5)
for(i in 1:length(difficulty_categories)) {
cat(" ", difficulty_categories[i], ":", recommended_percentages[i], "%\n")
}
cat("\n3. MƏZMUN BALANS STRATEGİYASI:\n")
cat(" - Hər məzmun sahəsi üçün kifayət tapşırıq\n")
cat(" - Bütün idrak səviyyələrinin təmsili\n")
cat(" - Müxtəlif sual formatlarının daxil edilməsi\n")
}
demonstrate_bank_principles()
## === TAPŞIRIQ BANKI DİZAYN PRİNSİPLƏRİ ===
##
## 1. BANK ÖLÇÜsÜ HESABLAMASi:
## Maksimum test uzunluğu: 30 tapşırıq
## Hədəf exposure nisbəti: 0.2
## Tövsiyə edilən bank ölçüsü: 150 tapşırıq
##
## 2. ÇƏTİNLİK PAYLANMASI STRATEGİYASI:
## Çox asan : 10 %
## Asan : 15 %
## Orta-asan : 20 %
## Orta : 20 %
## Orta-çətin : 20 %
## Çətin : 10 %
## Çox çətin : 5 %
##
## 3. MƏZMUN BALANS STRATEGİYASI:
## - Hər məzmun sahəsi üçün kifayət tapşırıq
## - Bütün idrak səviyyələrinin təmsili
## - Müxtəlif sual formatlarının daxil edilməsi
# 100 tapşırıqdan ibarət bank yaratmaq
create_item_bank <- function(n_items = 100, seed = 12345) {
set.seed(seed) # Təkrarlanabilir nəticələr üçün
# Çətinlik səviyyələrinin stratifikasiyası
difficulty_levels <- c(
rep(-2.5, 10), # Çox asan (10%)
rep(-1.5, 15), # Asan (15%)
rep(-0.5, 20), # Orta-asan (20%)
rep(0.0, 20), # Orta (20%)
rep(0.5, 20), # Orta-çətin (20%)
rep(1.5, 10), # Çətin (10%)
rep(2.5, 5) # Çox çətin (5%)
)
# Tapşırıq parametrlərinin yaradılması
item_bank <- data.frame(
item_id = 1:n_items,
a = runif(n_items, 0.8, 2.5), # Ayrıd edicilik
b = difficulty_levels + rnorm(n_items, 0, 0.2), # Çətinlik
c = runif(n_items, 0.1, 0.25), # Təsadüfi doğru cavab
content_area = sample(c("Riyaziyyat", "Fizika", "Kimya",
"Biologiya", "Tarix"), n_items, replace = TRUE),
cognitive_level = sample(c("Bilgi", "Anlayış", "Tətbiq",
"Analiz", "Sintez"), n_items, replace = TRUE),
time_limit = sample(60:180, n_items, replace = TRUE), # saniyə
difficulty_category = cut(difficulty_levels,
breaks = c(-Inf, -2, -1, 0, 1, 2, Inf),
labels = c("Çox asan", "Asan", "Orta-asan",
"Orta-çətin", "Çətin", "Çox çətin")),
created_date = Sys.Date(),
last_used = as.Date(NA),
usage_count = 0,
exposure_rate = 0.0
)
# Parametr keyfiyyətini yoxlayın və düzəldin
item_bank$a <- pmax(0.5, pmin(3.0, item_bank$a)) # a parametrini məhdudlaşdır
item_bank$c <- pmax(0.05, pmin(0.4, item_bank$c)) # c parametrini məhdudlaşdır
return(item_bank)
}
# Tapşırıq bankını yaradın
item_bank <- create_item_bank(100)
# İlk 5 tapşırığı göstər
cat("=== TAPŞIRIQ BANKI - İLK 5 TAPŞIRIQ ===\n")
## === TAPŞIRIQ BANKI - İLK 5 TAPŞIRIQ ===
## item_id a b c content_area cognitive_level time_limit
## 1 1 2.025537 -2.608077 0.1079032 Kimya Sintez 107
## 2 2 2.288814 -2.110461 0.1897986 Fizika Bilgi 163
## 3 3 2.093670 -2.489282 0.2062436 Tarix Sintez 99
## 4 4 2.306412 -2.429667 0.1980161 Kimya Anlayış 99
## 5 5 1.576018 -2.634195 0.1866121 Riyaziyyat Analiz 67
## difficulty_category
## 1 Çox asan
## 2 Çox asan
## 3 Çox asan
## 4 Çox asan
## 5 Çox asan
# Daha mürəkkəb tapşırıq bankı yaradma
create_advanced_item_bank <- function(n_items = 200,
content_specifications = NULL,
difficulty_distribution = "normal") {
set.seed(12345)
# Default məzmun spesifikasiyaları
if (is.null(content_specifications)) {
content_specifications <- list(
"Riyaziyyat" = list(weight = 0.3, subcategories = c("Ədəd", "Cəbr", "Həndəsə")),
"Elm" = list(weight = 0.4, subcategories = c("Fizika", "Kimya", "Biologiya")),
"Dil" = list(weight = 0.2, subcategories = c("Qrammatika", "Oxu", "Yaz")),
"Sosial" = list(weight = 0.1, subcategories = c("Tarix", "Coğrafiya"))
)
}
# Çətinlik paylanması
if (difficulty_distribution == "normal") {
difficulties <- rnorm(n_items, 0, 1.2)
} else if (difficulty_distribution == "uniform") {
difficulties <- runif(n_items, -3, 3)
} else { # stratified
difficulties <- create_stratified_difficulties(n_items)
}
# Məzmun sahələrini paylaşdır
content_assignment <- assign_content_areas(n_items, content_specifications)
# Bank yaradın
advanced_bank <- data.frame(
item_id = paste0("ITM", sprintf("%04d", 1:n_items)),
a = generate_discrimination_params(n_items),
b = difficulties,
c = generate_guessing_params(n_items),
content_area = content_assignment$main_area,
subcategory = content_assignment$subcategory,
cognitive_level = sample(c("Xatırla", "Anla", "Tətbiq et", "Təhlil et",
"Qiymətləndir", "Yarat"), n_items, replace = TRUE,
prob = c(0.2, 0.25, 0.25, 0.15, 0.1, 0.05)),
item_format = sample(c("MC4", "MC5", "TF", "SA"), n_items, replace = TRUE,
prob = c(0.6, 0.3, 0.05, 0.05)),
time_limit = round(rnorm(n_items, 120, 30)),
keywords = generate_keywords(n_items),
author = sample(c("Tərtibçi_A", "Tərtibçi_B", "Tərtibçi_C"),
n_items, replace = TRUE),
review_status = sample(c("Yeni", "Nəzərdən keçirilmiş", "Təsdiqlənmiş"),
n_items, replace = TRUE, prob = c(0.1, 0.3, 0.6)),
created_date = sample(seq(as.Date('2023/01/01'), as.Date('2024/12/31'), by="day"),
n_items, replace = TRUE),
stringsAsFactors = FALSE
)
return(advanced_bank)
}
# Köməkçi funksiyalar
create_stratified_difficulties <- function(n_items) {
# Stratifikasiya edilmiş çətinlik paylanması
strata <- c(-2.5, -1.5, -0.5, 0, 0.5, 1.5, 2.5)
proportions <- c(0.05, 0.15, 0.25, 0.3, 0.15, 0.08, 0.02)
difficulties <- c()
for(i in 1:length(strata)) {
n_in_stratum <- round(n_items * proportions[i])
if(n_in_stratum > 0) {
stratum_diffs <- rnorm(n_in_stratum, strata[i], 0.3)
difficulties <- c(difficulties, stratum_diffs)
}
}
# Lazım olarsa həcmi tam edin
while(length(difficulties) < n_items) {
difficulties <- c(difficulties, rnorm(1, 0, 1))
}
return(difficulties[1:n_items])
}
generate_discrimination_params <- function(n_items) {
# Yüksək keyfiyyətli ayrıd edicilik parametrləri
a_params <- rlnorm(n_items, meanlog = 0.2, sdlog = 0.3)
a_params <- pmax(0.7, pmin(3.5, a_params)) # 0.7-3.5 aralığında məhdudlaşdır
return(a_params)
}
generate_guessing_params <- function(n_items) {
# Realistik təsadüfi cavab parametrləri
c_params <- rbeta(n_items, 2, 10) # Ortalama ~0.17
c_params <- pmax(0.05, pmin(0.35, c_params))
return(c_params)
}
assign_content_areas <- function(n_items, content_specs) {
main_areas <- c()
subcategories <- c()
for(area in names(content_specs)) {
n_for_area <- round(n_items * content_specs[[area]]$weight)
if(n_for_area > 0) {
main_areas <- c(main_areas, rep(area, n_for_area))
subcats <- sample(content_specs[[area]]$subcategories, n_for_area, replace = TRUE)
subcategories <- c(subcategories, subcats)
}
}
# Lazım olarsa həcmi tam edin
while(length(main_areas) < n_items) {
area <- sample(names(content_specs), 1)
main_areas <- c(main_areas, area)
subcategories <- c(subcategories,
sample(content_specs[[area]]$subcategories, 1))
}
return(list(main_area = main_areas[1:n_items],
subcategory = subcategories[1:n_items]))
}
generate_keywords <- function(n_items) {
keyword_pool <- c("hesablama", "analiz", "sintez", "məntiq", "həll",
"tətbiq", "nəzəriyyə", "praktik", "müqayisə", "qiymətləndirmə")
keywords <- sapply(1:n_items, function(x) {
paste(sample(keyword_pool, sample(1:3, 1)), collapse = ", ")
})
return(keywords)
}
# Təkmilləşdirilmiş bank yaradın
advanced_bank <- create_advanced_item_bank(200)
cat("\n=== TƏKMİLLƏŞDİRİLMİŞ BANK - İLK 3 TAPŞIRIQ ===\n")
##
## === TƏKMİLLƏŞDİRİLMİŞ BANK - İLK 3 TAPŞIRIQ ===
## item_id a b c content_area subcategory
## 1 ITM0001 2.0391666 0.7026346 0.0500000 Riyaziyyat Həndəsə
## 2 ITM0002 1.0701135 0.8513592 0.1682811 Riyaziyyat Cəbr
## 3 ITM0003 0.8892331 -0.1311640 0.1531463 Riyaziyyat Ədəd
## cognitive_level item_format time_limit keywords
## 1 Anla MC5 91 analiz, praktik, həll
## 2 Təhlil et MC4 72 həll
## 3 Anla MC4 123 sintez
# Tapşırıq bankının təhlili
analyze_item_bank <- function(bank) {
cat("=== TAPŞIRIQ BANKI TƏHLİLİ ===\n\n")
# Əsas statistikalar
cat("1. ƏSAS STATİSTİKALAR:\n")
cat(" Ümumi tapşırıq sayı:", nrow(bank), "\n")
cat(" Orta çətinlik (b):", round(mean(bank$b), 3), "\n")
cat(" Çətinlik standart sapması:", round(sd(bank$b), 3), "\n")
cat(" Orta ayrıd edicilik (a):", round(mean(bank$a), 3), "\n")
cat(" Orta təsadüfi cavab (c):", round(mean(bank$c), 3), "\n\n")
# Çətinlik paylanması
cat("2. ÇƏTİNLİK PAYLANMASI:\n")
if("difficulty_category" %in% names(bank)) {
diff_table <- table(bank$difficulty_category)
for(i in 1:length(diff_table)) {
cat(" ", names(diff_table)[i], ":", diff_table[i],
"(", round(diff_table[i]/nrow(bank)*100, 1), "%)\n")
}
} else {
# Çətinlik kateqoriyalarını yaradın
diff_cats <- cut(bank$b, breaks = c(-Inf, -2, -1, 0, 1, 2, Inf),
labels = c("Çox asan", "Asan", "Orta-asan",
"Orta-çətin", "Çətin", "Çox çətin"))
diff_table <- table(diff_cats)
for(i in 1:length(diff_table)) {
cat(" ", names(diff_table)[i], ":", diff_table[i],
"(", round(diff_table[i]/nrow(bank)*100, 1), "%)\n")
}
}
cat("\n3. MƏZMUN SAHƏLƏRİ:\n")
content_table <- table(bank$content_area)
for(i in 1:length(content_table)) {
cat(" ", names(content_table)[i], ":", content_table[i],
"(", round(content_table[i]/nrow(bank)*100, 1), "%)\n")
}
cat("\n4. İDRAK SƏVİYYƏLƏRİ:\n")
if("cognitive_level" %in% names(bank)) {
cog_table <- table(bank$cognitive_level)
for(i in 1:length(cog_table)) {
cat(" ", names(cog_table)[i], ":", cog_table[i],
"(", round(cog_table[i]/nrow(bank)*100, 1), "%)\n")
}
}
# Keyfiyyət göstəriciləri
cat("\n5. KEYFİYYƏT GÖSTƏRİCİLƏRİ:\n")
low_discrimination <- sum(bank$a < 1.0)
high_guessing <- sum(bank$c > 0.3)
extreme_difficulty <- sum(abs(bank$b) > 3)
cat(" Aşağı ayrıd edicilik (a < 1.0):", low_discrimination,
"(", round(low_discrimination/nrow(bank)*100, 1), "%)\n")
cat(" Yüksək təsadüfi cavab (c > 0.3):", high_guessing,
"(", round(high_guessing/nrow(bank)*100, 1), "%)\n")
cat(" Həddindən artıq çətinlik (|b| > 3):", extreme_difficulty,
"(", round(extreme_difficulty/nrow(bank)*100, 1), "%)\n")
}
# Bank təhlili
analyze_item_bank(item_bank)
## === TAPŞIRIQ BANKI TƏHLİLİ ===
##
## 1. ƏSAS STATİSTİKALAR:
## Ümumi tapşırıq sayı: 100
## Orta çətinlik (b): -0.17
## Çətinlik standart sapması: 1.25
## Orta ayrıd edicilik (a): 1.666
## Orta təsadüfi cavab (c): 0.181
##
## 2. ÇƏTİNLİK PAYLANMASI:
## Çox asan : 10 ( 10 %)
## Asan : 15 ( 15 %)
## Orta-asan : 40 ( 40 %)
## Orta-çətin : 20 ( 20 %)
## Çətin : 10 ( 10 %)
## Çox çətin : 5 ( 5 %)
##
## 3. MƏZMUN SAHƏLƏRİ:
## Biologiya : 13 ( 13 %)
## Fizika : 17 ( 17 %)
## Kimya : 23 ( 23 %)
## Riyaziyyat : 28 ( 28 %)
## Tarix : 19 ( 19 %)
##
## 4. İDRAK SƏVİYYƏLƏRİ:
## Analiz : 20 ( 20 %)
## Anlayış : 23 ( 23 %)
## Bilgi : 24 ( 24 %)
## Sintez : 19 ( 19 %)
## Tətbiq : 14 ( 14 %)
##
## 5. KEYFİYYƏT GÖSTƏRİCİLƏRİ:
## Aşağı ayrıd edicilik (a < 1.0): 13 ( 13 %)
## Yüksək təsadüfi cavab (c > 0.3): 0 ( 0 %)
## Həddindən artıq çətinlik (|b| > 3): 0 ( 0 %)
# Tapşırıq bankının vizuallaşdırılması
visualize_item_bank <- function(bank) {
# 1. Parametr paylanmaları
p1 <- ggplot(bank, aes(x = a)) +
geom_histogram(bins = 20, fill = "lightblue", color = "black", alpha = 0.7) +
geom_vline(xintercept = mean(bank$a), color = "red", linetype = "dashed") +
labs(title = "Ayrıd Edicilik (a) Parametri Paylanması",
x = "Ayrıd Edicilik", y = "Tezlik") +
theme_minimal()
p2 <- ggplot(bank, aes(x = b)) +
geom_histogram(bins = 20, fill = "lightgreen", color = "black", alpha = 0.7) +
geom_vline(xintercept = mean(bank$b), color = "red", linetype = "dashed") +
labs(title = "Çətinlik (b) Parametri Paylanması",
x = "Çətinlik", y = "Tezlik") +
theme_minimal()
p3 <- ggplot(bank, aes(x = c)) +
geom_histogram(bins = 20, fill = "lightyellow", color = "black", alpha = 0.7) +
geom_vline(xintercept = mean(bank$c), color = "red", linetype = "dashed") +
labs(title = "Təsadüfi Cavab (c) Parametri Paylanması",
x = "Təsadüfi Cavab", y = "Tezlik") +
theme_minimal()
# 2. Parametr əlaqələri
p4 <- ggplot(bank, aes(x = b, y = a)) +
geom_point(alpha = 0.6, size = 2) +
geom_smooth(method = "lm", se = FALSE, color = "red") +
labs(title = "Çətinlik vs Ayrıd Edicilik",
x = "Çətinlik (b)", y = "Ayrıd Edicilik (a)") +
theme_minimal()
# 3. Məzmun sahələrinin paylanması
content_data <- bank %>%
count(content_area) %>%
mutate(percentage = round(n/sum(n)*100, 1))
p5 <- ggplot(content_data, aes(x = reorder(content_area, n), y = n, fill = content_area)) +
geom_col() +
geom_text(aes(label = paste0(n, " (", percentage, "%)")),
hjust = -0.1, size = 3) +
coord_flip() +
labs(title = "Məzmun Sahələrinin Paylanması",
x = "Məzmun Sahəsi", y = "Tapşırıq Sayı") +
theme_minimal() +
theme(legend.position = "none")
# 4. Çətinlik kateqoriyaları
if("difficulty_category" %in% names(bank)) {
p6 <- ggplot(bank, aes(x = difficulty_category, fill = difficulty_category)) +
geom_bar() +
labs(title = "Çətinlik Kateqoriyalarının Paylanması",
x = "Çətinlik Kateqoriyası", y = "Tapşırıq Sayı") +
theme_minimal() +
theme(axis.text.x = element_text(angle = 45, hjust = 1),
legend.position = "none")
} else {
bank$diff_cat <- cut(bank$b, breaks = c(-Inf, -2, -1, 0, 1, 2, Inf),
labels = c("Çox asan", "Asan", "Orta-asan",
"Orta-çətin", "Çətin", "Çox çətin"))
p6 <- ggplot(bank, aes(x = diff_cat, fill = diff_cat)) +
geom_bar() +
labs(title = "Çətinlik Kateqoriyalarının Paylanması",
x = "Çətinlik Kateqoriyası", y = "Tapşırıq Sayı") +
theme_minimal() +
theme(axis.text.x = element_text(angle = 45, hjust = 1),
legend.position = "none")
}
# Bütün qrafikleri birləşdir
grid.arrange(p1, p2, p3, p4, p5, p6, ncol = 2)
}
# Bank vizuallaşdırması
visualize_item_bank(item_bank)
# Bank keyfiyyətinin qiymətləndirilməsi
assess_bank_quality <- function(bank) {
cat("=== BANK KEYFİYYƏTİ QİYMƏTLƏNDİRMƏSİ ===\n\n")
# Keyfiyyət kriteriləri
quality_criteria <- list(
discrimination_threshold = 1.0, # a > 1.0
guessing_threshold = 0.3, # c < 0.3
difficulty_range = c(-3, 3), # -3 < b < 3
min_content_representation = 10 # Hər məzmun sahəsi üçün minimum
)
# 1. Ayrıd edicilik keyfiyyəti
high_discrimination <- sum(bank$a >= quality_criteria$discrimination_threshold)
discrimination_score <- high_discrimination / nrow(bank) * 100
cat("1. AYRID EDİCİLİK KEYFİYYƏTİ:\n")
cat(" Yüksək ayrıd edicilik (a ≥ 1.0):", high_discrimination, "/", nrow(bank),
"(", round(discrimination_score, 1), "%)\n")
if(discrimination_score >= 80) {
cat(" Qiymət: ✅ Əla\n")
} else if(discrimination_score >= 60) {
cat(" Qiymət: ⚡ Yaxşı\n")
} else {
cat(" Qiymət: ⚠️ Təkmilləşdirməyə ehtiyac\n")
}
# 2. Təsadüfi cavab keyfiyyəti
low_guessing <- sum(bank$c < quality_criteria$guessing_threshold)
guessing_score <- low_guessing / nrow(bank) * 100
cat("\n2. TƏSADÜFI CAVAB KEYFİYYƏTİ:\n")
cat(" Aşağı təsadüfi cavab (c < 0.3):", low_guessing, "/", nrow(bank),
"(", round(guessing_score, 1), "%)\n")
if(guessing_score >= 90) {
cat(" Qiymət: ✅ Əla\n")
} else if(guessing_score >= 75) {
cat(" Qiymət: ⚡ Yaxşı\n")
} else {
cat(" Qiymət: ⚠️ Təkmilləşdirməyə ehtiyac\n")
}
# 3. Çətinlik aralığı
appropriate_difficulty <- sum(bank$b >= quality_criteria$difficulty_range[1] &
bank$b <= quality_criteria$difficulty_range[2])
difficulty_score <- appropriate_difficulty / nrow(bank) * 100
cat("\n3. ÇƏTİNLİK ARALIĞI KEYFİYYƏTİ:\n")
cat(" Uyğun çətinlik (-3 ≤ b ≤ 3):", appropriate_difficulty, "/", nrow(bank),
"(", round(difficulty_score, 1), "%)\n")
if(difficulty_score >= 95) {
cat(" Qiymət: ✅ Əla\n")
} else if(difficulty_score >= 85) {
cat(" Qiymət: ⚡ Yaxşı\n")
} else {
cat(" Qiymət: ⚠️ Təkmilləşdirməyə ehtiyac\n")
}
# 4. Məzmun əhatəsi
content_counts <- table(bank$content_area)
adequate_content <- sum(content_counts >= quality_criteria$min_content_representation)
content_score <- adequate_content / length(content_counts) * 100
cat("\n4. MƏZMUN ƏHATƏ KEYFİYYƏTİ:\n")
cat(" Kifayət məzmun sahələri:", adequate_content, "/", length(content_counts),
"(", round(content_score, 1), "%)\n")
if(content_score >= 100) {
cat(" Qiymət: ✅ Əla\n")
} else if(content_score >= 80) {
cat(" Qiymət: ⚡ Yaxşı\n")
} else {
cat(" Qiymət: ⚠️ Təkmilləşdirməyə ehtiyac\n")
}
# Ümumi qiymət
overall_score <- mean(c(discrimination_score, guessing_score,
difficulty_score, content_score))
cat("\n5. ÜMUMİ KEYFİYYƏT BALI:\n")
cat(" Ümumi bal:", round(overall_score, 1), "/100\n")
if(overall_score >= 85) {
cat(" Qiymət: ✅ Əla keyfiyyət - Bank CAT üçün hazırdır\n")
bank_grade <- "A"
} else if(overall_score >= 75) {
cat(" Qiymət: ⚡ Yaxşı keyfiyyət - Kiçik təkmilləşdirmələr məsləhət görülür\n")
bank_grade <- "B"
} else if(overall_score >= 65) {
cat(" Qiymət: ⚠️ Orta keyfiyyət - Təkmilləşdirmə lazımdır\n")
bank_grade <- "C"
} else {
cat(" Qiymət: ❌ Aşağı keyfiyyət - Əsaslı yenidən işlənmə lazımdır\n")
bank_grade <- "D"
}
return(list(
overall_score = overall_score,
discrimination_score = discrimination_score,
guessing_score = guessing_score,
difficulty_score = difficulty_score,
content_score = content_score,
grade = bank_grade
))
}
# Bank keyfiyyət qiymətləndirilməsi
quality_assessment <- assess_bank_quality(item_bank)
## === BANK KEYFİYYƏTİ QİYMƏTLƏNDİRMƏSİ ===
##
## 1. AYRID EDİCİLİK KEYFİYYƏTİ:
## Yüksək ayrıd edicilik (a ≥ 1.0): 87 / 100 ( 87 %)
## Qiymət: ✅ Əla
##
## 2. TƏSADÜFI CAVAB KEYFİYYƏTİ:
## Aşağı təsadüfi cavab (c < 0.3): 100 / 100 ( 100 %)
## Qiymət: ✅ Əla
##
## 3. ÇƏTİNLİK ARALIĞI KEYFİYYƏTİ:
## Uyğun çətinlik (-3 ≤ b ≤ 3): 100 / 100 ( 100 %)
## Qiymət: ✅ Əla
##
## 4. MƏZMUN ƏHATƏ KEYFİYYƏTİ:
## Kifayət məzmun sahələri: 5 / 5 ( 100 %)
## Qiymət: ✅ Əla
##
## 5. ÜMUMİ KEYFİYYƏT BALI:
## Ümumi bal: 96.8 /100
## Qiymət: ✅ Əla keyfiyyət - Bank CAT üçün hazırdır
# Test Məlumat Funksiyasının hesablanması
calculate_test_information <- function(bank, theta_range = c(-4, 4)) {
theta <- seq(theta_range[1], theta_range[2], 0.1)
total_information <- numeric(length(theta))
# Hər tapşırıq üçün məlumat funksiyasını hesablayın
for(i in 1:nrow(bank)) {
a <- bank$a[i]
b <- bank$b[i]
c <- bank$c[i]
# P(θ) hesablayın
P <- c + (1 - c) * plogis(a * (theta - b))
# İtem məlumat funksiyası: I(θ) = a² * P'(θ)² / [P(θ) * (1 - P(θ))]
# P'(θ) = a * (1-c) * P(θ) * (1-P(θ)) / (1-c*Q(θ))
Q <- 1 - P
P_star <- (P - c) / (1 - c)
Q_star <- 1 - P_star
item_info <- (a^2 * P_star * Q_star) / (P * Q)
# NaN dəyərləri 0 ilə əvəz edin
item_info[is.nan(item_info) | is.infinite(item_info)] <- 0
total_information <- total_information + item_info
}
return(data.frame(theta = theta, information = total_information))
}
# Test məlumat funksiyasını hesablayın və vizuallaşdırın
tif_data <- calculate_test_information(item_bank)
# TIF qrafiki
ggplot(tif_data, aes(x = theta, y = information)) +
geom_line(size = 1.5, color = "blue") +
labs(
title = "Test Məlumat Funksiyası (TIF)",
subtitle = paste("Ümumi", nrow(item_bank), "tapşırıq"),
x = "Qabiliyyət Səviyyəsi (θ)",
y = "Test Məlumatı"
) +
theme_minimal() +
geom_vline(xintercept = 0, linetype = "dashed", alpha = 0.5) +
annotate("text", x = 0.5, y = max(tif_data$information) * 0.9,
label = paste("Maksimum məlumat:", round(max(tif_data$information), 2)))
## === TEST MƏLUMAT FUNKSİYASI STATİSTİKALARI ===
## Maksimum məlumat: 372.2
## Məlumat maksimumunun θ dəyəri: 4
## θ = 0 nöqtəsində məlumat: 282.21
cat("Orta məlumat (θ ∈ [-2, 2]):",
round(mean(tif_data$information[tif_data$theta >= -2 & tif_data$theta <= 2]), 2), "\n")
## Orta məlumat (θ ∈ [-2, 2]): 262.9
# Bank balansını optimallaşdırma
optimize_bank_balance <- function(bank, target_difficulty_distribution = NULL) {
if(is.null(target_difficulty_distribution)) {
target_difficulty_distribution <- data.frame(
category = c("Çox asan", "Asan", "Orta-asan", "Orta-çətin", "Çətin", "Çox çətin"),
target_percent = c(10, 15, 25, 25, 15, 10),
b_range_min = c(-Inf, -2, -1, 0, 1, 2),
b_range_max = c(-2, -1, 0, 1, 2, Inf)
)
}
cat("=== BANK BALANS OPTİMALLAŞDIRMASI ===\n\n")
# Cari paylanma
bank$difficulty_cat <- cut(bank$b,
breaks = c(-Inf, -2, -1, 0, 1, 2, Inf),
labels = target_difficulty_distribution$category)
current_distribution <- bank %>%
count(difficulty_cat) %>%
mutate(current_percent = round(n / nrow(bank) * 100, 1))
# Hədəf ilə müqayisə
comparison <- merge(target_difficulty_distribution, current_distribution,
by.x = "category", by.y = "difficulty_cat", all = TRUE)
comparison[is.na(comparison)] <- 0
comparison$difference <- comparison$current_percent - comparison$target_percent
cat("CARI vs HƏDƏF PAYLANMA:\n")
print(comparison[, c("category", "target_percent", "current_percent", "difference")])
# Optimallaşdırma tövsiyələri
cat("\nOPTİMALLAŞDIRMA TOVSİYƏLƏRİ:\n")
for(i in 1:nrow(comparison)) {
if(abs(comparison$difference[i]) > 5) {
if(comparison$difference[i] > 0) {
cat("- ", comparison$category[i], "kateqoriyasında",
abs(round(comparison$difference[i])), "% artıq tapşırıq var\n")
} else {
cat("- ", comparison$category[i], "kateqoriyasında",
abs(round(comparison$difference[i])), "% az tapşırıq var\n")
}
}
}
return(comparison)
}
# Bank balansını optimallaşdır
balance_analysis <- optimize_bank_balance(item_bank)
## === BANK BALANS OPTİMALLAŞDIRMASI ===
##
## CARI vs HƏDƏF PAYLANMA:
## category target_percent current_percent difference
## 1 Asan 15 15 0
## 2 Çətin 15 11 -4
## 3 Çox asan 10 10 0
## 4 Çox çətin 10 5 -5
## 5 Orta-asan 25 31 6
## 6 Orta-çətin 25 28 3
##
## OPTİMALLAŞDIRMA TOVSİYƏLƏRİ:
## - Orta-asan kateqoriyasında 6 % artıq tapşırıq var
# Problemli tapşırıqları aşkarlayan funksiya
identify_problematic_items <- function(bank) {
cat("=== PROBLEMLİ TAPŞIRIQLAR ANALİZİ ===\n\n")
# Problem kriteriləri
problems <- data.frame(
item_id = bank$item_id,
low_discrimination = bank$a < 0.8,
high_guessing = bank$c > 0.35,
extreme_difficulty = abs(bank$b) > 3,
very_low_discrimination = bank$a < 0.5,
negative_discrimination = bank$a < 0
)
# Hər tapşırıq üçün problem sayını hesablayın
problems$total_problems <- rowSums(problems[, 2:6])
# Problem kateqoriyaları
severe_problems <- problems[problems$total_problems >= 3, ]
moderate_problems <- problems[problems$total_problems == 2, ]
minor_problems <- problems[problems$total_problems == 1, ]
cat("PROBLEM KATEQORİYALARI:\n")
cat("Ağır problemli tapşırıqlar (3+ problem):", nrow(severe_problems), "\n")
cat("Orta problemli tapşırıqlar (2 problem):", nrow(moderate_problems), "\n")
cat("Kiçik problemli tapşırıqlar (1 problem):", nrow(minor_problems), "\n")
cat("Problemsiz tapşırıqlar:", nrow(bank) - nrow(severe_problems) -
nrow(moderate_problems) - nrow(minor_problems), "\n\n")
# Ağır problemli tapşırıqların detalları
if(nrow(severe_problems) > 0) {
cat("AĞIR PROBLEMLİ TAPŞIRIQLAR:\n")
for(i in 1:min(10, nrow(severe_problems))) { # İlk 10-u göstər
item_id <- severe_problems$item_id[i]
item_data <- bank[bank$item_id == item_id, ]
cat("Tapşırıq", item_id, ": a =", round(item_data$a, 3),
", b =", round(item_data$b, 3), ", c =", round(item_data$c, 3), "\n")
}
}
# Tövsiyələr
cat("\nTƏKMİLLƏŞDİRMƏ TOVSİYƏLƏRİ:\n")
if(nrow(severe_problems) > 0) {
cat("1. Ağır problemli", nrow(severe_problems), "tapşırığı bankdan çıxarın\n")
}
if(nrow(moderate_problems) > 0) {
cat("2. Orta problemli", nrow(moderate_problems), "tapşırığı yenidən nəzərdən keçirin\n")
}
if(nrow(minor_problems) > 0) {
cat("3. Kiçik problemli", nrow(minor_problems), "tapşırığı izləyin\n")
}
return(list(
severe = severe_problems,
moderate = moderate_problems,
minor = minor_problems,
summary = problems
))
}
# Problemli tapşırıqları aşkar edin
problematic_items <- identify_problematic_items(item_bank)
## === PROBLEMLİ TAPŞIRIQLAR ANALİZİ ===
##
## PROBLEM KATEQORİYALARI:
## Ağır problemli tapşırıqlar (3+ problem): 0
## Orta problemli tapşırıqlar (2 problem): 0
## Kiçik problemli tapşırıqlar (1 problem): 0
## Problemsiz tapşırıqlar: 100
##
##
## TƏKMİLLƏŞDİRMƏ TOVSİYƏLƏRİ:
# Exposure control sistemlərinin simulyasiyası
simulate_exposure_control <- function(bank, n_examinees = 1000, max_test_length = 25) {
cat("=== EXPOSURE CONTROL SİMULYASİYASI ===\n\n")
# Hər tapşırığın istifadə sayını simulyasiya edin
set.seed(12345)
# Sadə exposure simulyasiyası
# Yüksək keyfiyyətli tapşırıqlar daha çox istifadə olunur
quality_weights <- pmax(0.1, bank$a - 0.5) # Ayrıd ediciliyə əsaslı çəki
exposure_counts <- numeric(nrow(bank))
for(examinee in 1:n_examinees) {
# Hər test alan üçün təsadüfi test uzunluğu
test_length <- sample(15:max_test_length, 1)
# Çəkili təsadüfi seçim
selected_items <- sample(1:nrow(bank), test_length,
prob = quality_weights, replace = FALSE)
exposure_counts[selected_items] <- exposure_counts[selected_items] + 1
}
# Exposure nisbətlərini hesablayın
bank$exposure_count <- exposure_counts
bank$exposure_rate <- exposure_counts / n_examinees
# Exposure statistikaları
cat("EXPOSURE STATİSTİKALARI:\n")
cat("Orta exposure nisbəti:", round(mean(bank$exposure_rate), 3), "\n")
cat("Maksimum exposure nisbəti:", round(max(bank$exposure_rate), 3), "\n")
cat("Minimum exposure nisbəti:", round(min(bank$exposure_rate), 3), "\n")
cat("Exposure standart sapması:", round(sd(bank$exposure_rate), 3), "\n\n")
# Yüksək exposure tapşırıqları
high_exposure_threshold <- 0.4
high_exposure_items <- bank[bank$exposure_rate > high_exposure_threshold, ]
cat("YÜKSƏK EXPOSURE TAPŞIRIQLAR (>", high_exposure_threshold, "):\n")
cat("Sayı:", nrow(high_exposure_items), "\n")
if(nrow(high_exposure_items) > 0) {
cat("Tapşırıq ID-ləri:", paste(head(high_exposure_items$item_id, 10), collapse = ", "), "\n")
}
# Aşağı exposure tapşırıqları
low_exposure_threshold <- 0.05
low_exposure_items <- bank[bank$exposure_rate < low_exposure_threshold, ]
cat("\nAŞAĞI EXPOSURE TAPŞIRIQLAR (<", low_exposure_threshold, "):\n")
cat("Sayı:", nrow(low_exposure_items), "\n")
if(nrow(low_exposure_items) > 0) {
cat("Tapşırıq ID-ləri:", paste(head(low_exposure_items$item_id, 10), collapse = ", "), "\n")
}
# Exposure paylanması vizuallaşdırması
exposure_plot <- ggplot(bank, aes(x = exposure_rate)) +
geom_histogram(bins = 20, fill = "lightcoral", color = "black", alpha = 0.7) +
geom_vline(xintercept = mean(bank$exposure_rate), color = "red", linetype = "dashed") +
labs(
title = "Tapşırıq Exposure Nisbətlərinin Paylanması",
subtitle = paste("n =", n_examinees, "test alanlar,", "orta test uzunluğu ≈",
round(mean(15:max_test_length))),
x = "Exposure Nisbəti",
y = "Tapşırıq Sayı"
) +
theme_minimal()
print(exposure_plot)
return(bank)
}
# Exposure control simulyasiyası
bank_with_exposure <- simulate_exposure_control(item_bank, n_examinees = 1000)
## === EXPOSURE CONTROL SİMULYASİYASI ===
##
## EXPOSURE STATİSTİKALARI:
## Orta exposure nisbəti: 0.201
## Maksimum exposure nisbəti: 0.343
## Minimum exposure nisbəti: 0.054
## Exposure standart sapması: 0.083
##
## YÜKSƏK EXPOSURE TAPŞIRIQLAR (> 0.4 ):
## Sayı: 0
##
## AŞAĞI EXPOSURE TAPŞIRIQLAR (< 0.05 ):
## Sayı: 0
# Bank təhlükəsizliyinin qiymətləndirilməsi
assess_bank_security <- function(bank_with_exposure) {
cat("=== BANK TƏHLÜKƏSİZLİK QİYMƏTLƏNDİRMƏSİ ===\n\n")
# Təhlükəsizlik metriklər
# 1. Exposure variasiyası
exposure_cv <- sd(bank_with_exposure$exposure_rate) / mean(bank_with_exposure$exposure_rate)
cat("1. EXPOSURE VARİASİYASI:\n")
cat(" Coefficient of Variation:", round(exposure_cv, 3), "\n")
if(exposure_cv < 0.3) {
cat(" Qiymət: ✅ Yaxşı exposure balansı\n")
} else if(exposure_cv < 0.5) {
cat(" Qiymət: ⚡ Orta exposure balansı\n")
} else {
cat(" Qiymət: ⚠️ Zəif exposure balansı\n")
}
# 2. Tapşırıq pool ölçüsü
max_test_length <- 25
pool_ratio <- nrow(bank_with_exposure) / max_test_length
cat("\n2. TAPŞIRIQ POOL ÖLÇÜsÜ:\n")
cat(" Pool/Test nisbəti:", round(pool_ratio, 1), "\n")
if(pool_ratio >= 5) {
cat(" Qiymət: ✅ Kifayət bank ölçüsü\n")
} else if(pool_ratio >= 3) {
cat(" Qiymət: ⚡ Orta bank ölçüsü\n")
} else {
cat(" Qiymət: ⚠️ Kiçik bank ölçüsü\n")
}
# 3. Məzmun sahələrinin paylanması
content_balance <- table(bank_with_exposure$content_area)
content_cv <- sd(content_balance) / mean(content_balance)
cat("\n3. MƏZMUN BALANSLAŞDIRMASI:\n")
cat(" Məzmun CV:", round(content_cv, 3), "\n")
if(content_cv < 0.3) {
cat(" Qiymət: ✅ Yaxşı məzmun balansı\n")
} else if(content_cv < 0.5) {
cat(" Qiymət: ⚡ Orta məzmun balansı\n")
} else {
cat(" Qiymət: ⚠️ Zəif məzmun balansı\n")
}
# 4. Yüksək exposure risk
high_risk_items <- sum(bank_with_exposure$exposure_rate > 0.5)
risk_percentage <- high_risk_items / nrow(bank_with_exposure) * 100
cat("\n4. YÜKSƏK EXPOSURE RİSKİ:\n")
cat(" Yüksək risk tapşırıqları:", high_risk_items, "(", round(risk_percentage, 1), "%)\n")
if(risk_percentage < 5) {
cat(" Qiymət: ✅ Aşağı təhlükəsizlik riski\n")
} else if(risk_percentage < 10) {
cat(" Qiymət: ⚡ Orta təhlükəsizlik riski\n")
} else {
cat(" Qiymət: ⚠️ Yüksək təhlükəsizlik riski\n")
}
# Ümumi təhlükəsizlik bali
security_score <- mean(c(
ifelse(exposure_cv < 0.3, 100, ifelse(exposure_cv < 0.5, 75, 50)),
ifelse(pool_ratio >= 5, 100, ifelse(pool_ratio >= 3, 75, 50)),
ifelse(content_cv < 0.3, 100, ifelse(content_cv < 0.5, 75, 50)),
ifelse(risk_percentage < 5, 100, ifelse(risk_percentage < 10, 75, 50))
))
cat("\n5. ÜMUMİ TƏHLÜKƏSİZLİK BALI:", round(security_score, 1), "/100\n")
if(security_score >= 85) {
cat(" Qiymət: ✅ Yüksək təhlükəsizlik\n")
} else if(security_score >= 70) {
cat(" Qiymət: ⚡ Orta təhlükəsizlik\n")
} else {
cat(" Qiymət: ⚠️ Aşağı təhlükəsizlik - İyileşdirmə lazımdır\n")
}
return(security_score)
}
# Bank təhlükəsizlik qiymətləndirilməsi
security_score <- assess_bank_security(bank_with_exposure)
## === BANK TƏHLÜKƏSİZLİK QİYMƏTLƏNDİRMƏSİ ===
##
## 1. EXPOSURE VARİASİYASI:
## Coefficient of Variation: 0.411
## Qiymət: ⚡ Orta exposure balansı
##
## 2. TAPŞIRIQ POOL ÖLÇÜsÜ:
## Pool/Test nisbəti: 4
## Qiymət: ⚡ Orta bank ölçüsü
##
## 3. MƏZMUN BALANSLAŞDIRMASI:
## Məzmun CV: 0.287
## Qiymət: ✅ Yaxşı məzmun balansı
##
## 4. YÜKSƏK EXPOSURE RİSKİ:
## Yüksək risk tapşırıqları: 0 ( 0 %)
## Qiymət: ✅ Aşağı təhlükəsizlik riski
##
## 5. ÜMUMİ TƏHLÜKƏSİZLİK BALI: 87.5 /100
## Qiymət: ✅ Yüksək təhlükəsizlik
Bu bölmədə CAT sistemləri üçün keyfiyyətli tapşırıq bankının necə yaradılacağını və idarə ediləcəyini öyrəndik. Tapşırıq bankı CAT-ın ürəyidir və onun keyfiyyəti sistemin ümumi performansını müəyyən edir.
Bank ölçüsü maksimum test uzunluğunun ən azı 5 misli olmalıdır
Hər məzmun sahəsində kifayət sayda tapşırıq olmalıdır
Exposure nisbətləri mütəmadi izlənməli və optimallaşdırılmalıdır
Problemli tapşırıqlar vaxtında aşkarlanmalı və əvəz edilməlidir
Bölmə 7: CAT Adaptiv Alqoritmlərinin Tənzimlənməsi
Bölmə 8: CAT Simulyasiyalarının Aparılması
Bölmə 9: CAT Performansının Qiymətləndirilməsi
Qeyd: Bu bölmədə yaradılan tapşırıq bankı simulyasiya məqsədli nümunədir. Real CAT sistemləri üçün empirik verilənlərdən əldə edilmiş və ekspert qiymətləndirilməsindən keçmiş tapşırıq parametrləri istifadə edilməlidir.