Итераторы Go 1.23, унификация стандартов и улучшение экосистемы Go
Итераторы Go 1.23, унификация стандартов и улучшение экосистемы Go

Предисловие

Go 1.23 Версия существует по пекинскому времени 2024 Год 8 луна 14 раннее утро 1:03 выпускать。Эта версия содержит несколько крупных обновлений.,Конкретное содержание можно найти в моем предыдущемизстатья:Вышла версия Go 1.23, вы должны знать эти важные обновления!。本文将重点介绍 iterator Стандартный Итератор。

Вы готовы? Возьмите чашку любимого кофе или чая и узнайте, прочитав эту статью.

Почему были введены стандартные итераторы

Итераторсуществовать Go Эта концепция не нова в языке. Фактически, она существует с тех пор, как существует. Go в экосистеме. Если вы часто используете Go стандартная библиотека,Возможно, вы заметили, что некоторые библиотеки предоставляют реализацию Итератора.,Например:bufio.Scannerdatabase.Rowsfilepath.Walk(Dir)flag.Visit и sync.Map.Range ждать. Так почему Go Будет ли чиновник по-прежнему предоставлять единые стандарты из Итератора? Основная причина существования заключается в том, что существующие конструкции и способы использования различаются. Когда мы используем новую библиотеку, нам обычно нужно научиться ею пользоваться. Если стандартизированную форму Итераториза можно унифицировать, нам нужно только освоить стандартное определение и использование Итераториза, и мы сможем адаптироваться ко всем Итераторизу.

Итератор

существовать Go 1.23 середина,Итератор Фактически, это относится к функции, которая соответствует одной из следующих трех сигнатур функции:

Язык кода:go
копировать
func(yield func() bool)

func(yield func(V) bool)

func(yield func(K, V) bool)

Если значение, возвращаемое функцией или методом, соответствует одной из приведенных выше форм, то возвращаемое значение можно вызвать Итератор

Итератор делится на Нажмите Итератор и Ла Итератор,Вышеуказанная конструкция является типичнойиз Нажмите Итератор,Позвонив yield Функция проходит через ряд значений,yield функция возвращает bool,Решите, продолжать ли развертывание.

Пример кода:

Язык кода:go
копировать
func Backward[E any](s []E) func(yield func(int, E) bool) {
    return func(yield func(int, E) bool) {
        for i := len(s) - 1; i >= 0; i-- {
            if !yield(i, s[i]) {
                return
            }
        }
    }
}

существуют В этом примере Итератор будет проходить в обратном порядке s элементы в срезе и передать yield Функция выталкивает каждый элемент. если yield возвращаться false,Обход прекратится преждевременно.

Диапазон по типам функций (обход типов функций)

Прочитав предыдущую реализацию из Итератора, вы запутались: Итератор передается путем вызова yield Функция постепенно выводит значение элемента, так как же нам получить значение, полученное от Итератора? Ответ заключается в использовании for-range цикл.

существовать Go 1.23 版本середина,for-range Выражения диапазона в циклах были улучшены. Ранее выражения диапазона поддерживались только array(множество)、slice(кусочек) и map(картографирование) и т. д. типов и от Go 1.23 начинать,Добавлена ​​поддержка типов функций из. но,Тип функции должен быть одним из трех типов, упомянутых выше.,То есть функцию необходимо реализовать Итератор.

Пример кода:

Язык кода:go
копировать
package main

import "fmt"

func main() {
	s := []string{"Программист", "Чен Минён"}
	for i, v := range Backward(s) {
		fmt.Println(i, v)
	}
}

// Backward Итерация в обратном порядке
func Backward[E any](s []E) func(yield func(int, E) bool) {
	return func(yield func(int, E) bool) {
		for i := len(s) - 1; i >= 0; i-- {
			if !yield(i, s[i]) {
				return
			}
		}
	}
}

Результаты запуска программы:

Язык кода:bash
копировать
1 Чен Минён
0 программист

iter Сумка

Для упрощения использования Итераториз,Go 1.23 Добавлена ​​новая версия iter Сумка, Сумка определяет два типа Итераторов, а именно Seq и Seq2,Используется для обработки различных сценариев итерации.

Язык кода:go
копировать
package iter

type Seq[V any] func(yield func(V) bool)

type Seq2[K, V any] func(yield func(K, V) bool)

Seq и Seq2 Разница:

  • Seq[V any]undefinedSeq это универсальный тип функции, которая получает yield функция как параметр。он запускает один элемент,Напримеркусочекиз索引或картографированиесерединаизключ。yield функция возвращает bool,Решите, продолжать ли итерацию.

Сценарий использования: Может использоваться для получения одного значения в результате итерации.,Например, индекс или значение в срезе,Или ключ или значение на карте.

  • Seq2[K, V any]undefinedSeq2 это универсальный тип функции, которая получает yield функция,Нажмите пару элементов,Например, индекс и значение в срезе,或者картографированиесерединаизключ值对。yield функция同样возвращаться bool,к Решите, продолжать ли итерацию.

Сценарий использования: используется, когда необходимо получить доступ к двум значениям (например, ключам и значениям) одновременно.

существуют Набор случаев использования Итераториз в наборе

Язык кода:go
копировать
type Set[E comparable] struct {
	m map[E]struct{}
}

func NewSet[E comparable]() Set[E] {
	return Set[E]{m: make(map[E]struct{})}
}

func (s Set[E]) Add(e E) {
	s.m[e] = struct{}{}
}

func (s Set[E]) Remove(e E) {
	delete(s.m, e)
}

func (s Set[E]) Contains(e E) bool {
	_, ok := s.m[e]
	return ok
}

Вышеупомянутое является простым универсальным Set Реализация коллекции, коллекция Сумка содержит тип map[E]struct{} из m Поле,Используется для хранения элементов коллекции.。Set В сборнике также представлены Add(Добавить элемент)、Remove(Удалять)и Contains(Определить, существует ли элементсуществовать)Три основных метода。

потому что m Поле не экспортируется, и разработчик не может напрямую получить к нему доступ в других полях. Если разработчик хочет пройти по элементам коллекции, то есть пройти m Как реализовать маппинг? Мы можем настроить метод Итератора или появиться m Отображение предназначено для того, чтобы пользователи могли перемещаться самостоятельно. Однако, что более важно, мы можем использовать Go 1.23 Предоставляет механизм из Итератор для реализации этой функциональности.

Язык кода:go
копировать
func (s Set[E]) All() iter.Seq[E] {
	return func(yield func(E) bool) {
		for v := range s.m {
			if !yield(v) {
				return
			}
		}
	}
}

Полный пример кода:

Язык кода:go
копировать
package main

import (
	"fmt"
	"iter"
)

type Set[E comparable] struct {
	m map[E]struct{}
}

func NewSet[E comparable]() Set[E] {
	return Set[E]{m: make(map[E]struct{})}
}

func (s Set[E]) Add(e E) {
	s.m[e] = struct{}{}
}

func (s Set[E]) Remove(e E) {
	delete(s.m, e)
}

func (s Set[E]) Contains(e E) bool {
	_, ok := s.m[e]
	return ok
}

func (s Set[E]) All() iter.Seq[E] {
	return func(yield func(E) bool) {
		for v := range s.m {
			if !yield(v) {
				return
			}
		}
	}
}

func main() {
	set := NewSet[string]()
	set.Add("Программист")
	set.Add("Чен Минён")

	for v := range set.All() {
		fmt.Println(v)
	}
}

Результаты запуска программы:

Язык кода:bash
копировать
программист
Чен Минён

Ла Итератор

существовать讲 Ла Итератор Прежде, давайте сначала поймем Нажмите Ла Итератор Оба различия:

  • Нажмите Итератор Активно перемещайте каждое значение в контейнере, чтобы yield функциясередина。существовать Go язык, мы можем пройти for-range Цикл напрямую получает отправленное значение.
  • Вопреки этому,Ла Итератор Вызывающий абонент активно запрашивает данные. Каждый раз, когда ты звонишь Ла Итератор время,它从容器середина拉出下一个值ивозвращаться。Хотя for/range Заявление не поддерживает напрямую Ла Итератор,Но через обычныеиз for 循环可к轻松实现对Ла Итераториз Итерировать。

стоит быть счастливым из,Нам не нужно вручную реализовывать Ла Итератор,потому что iter предоставлено Сумкой Pull функция, которая получает Стандартный (Push) Итератор Тип из параметра, получается два параметра, первый параметр Ла Итератор,Второй параметр останавливаться функция. Когда нам больше не нужно будет вытаскивать элемент из, вызовем останавливаться Просто функционируйте.

Пример кода:

Язык кода:go
копировать
package main

import (
	"fmt"
	"iter"
)

type Set[E comparable] struct {
	m map[E]struct{}
}

func NewSet[E comparable]() Set[E] {
	return Set[E]{m: make(map[E]struct{})}
}

func (s Set[E]) Add(e E) {
	s.m[e] = struct{}{}
}

func (s Set[E]) Remove(e E) {
	delete(s.m, e)
}

func (s Set[E]) Contains(e E) bool {
	_, ok := s.m[e]
	return ok
}

func (s Set[E]) All() iter.Seq[E] {
	return func(yield func(E) bool) {
		for v := range s.m {
			if !yield(v) {
				return
			}
		}
	}
}

func main() {
	set := NewSet[string]()
	set.Add("Программист")
	set.Add("Чен Минён")

	next, stop := iter.Pull(set.All())
	for {
		v, ok := next()
		if !ok {
			break
		}
		fmt.Println(v)
		stop()
	}
}

Активный звонок stop функция приведет к yield функция提前возвращаться false,так что проходи next Функция получает из ok также будет false,Указывает конец итерации,Больше элементов получить невозможно.

Результаты запуска программы:

Язык кода:bash
копировать
программист

В стандартную библиотеку добавлена ​​новая функция из Итератор.

С введением Итераториз,slices и maps Сумка также добавляет несколько новых функций для использования с Итераториз.

slices Сумма, недавно добавленная из функции:

  • All([]E) iter.Seq2[int, E]
  • Values([]E) iter.Seq[E]
  • Collect(iter.Seq[E]) []E
  • AppendSeq([]E, iter.Seq[E]) []E
  • Backward([]E) iter.Seq2[int, E]
  • Sorted(iter.Seq[E]) []E
  • SortedFunc(iter.Seq[E], func(E, E) int) []E
  • SortedStableFunc(iter.Seq[E], func(E, E) int) []E
  • Repeat([]E, int) []E
  • Chunk([]E, int) iter.Seq([]E)

Информацию об использовании этих функций см. slices Сумкадокумент

maps Сумма, недавно добавленная из функции:

  • All(map[K]V) iter.Seq2[K, V]
  • Keys(map[K]V) iter.Seq[K]
  • Values(map[K]V) iter.Seq[V]
  • Collect(iter.Seq2[K, V]) map[K, V]
  • Insert(map[K, V], iter.Seq2[K, V])

Информацию об использовании этих функций см. maps Сумкадокумент

краткое содержание

В этой статье подробно рассказывается Go 1.23 Версия в из Итераторе. Содержание охватывает введение Стандартный Итератор из Основные причины, определение Итератора и как его использовать. Кроме того, обсуждалось также iter Расширение функции Сумкаиз и slices и maps из и функции, связанные с Итератором, были добавлены в стандартную библиотеку.

Некоторые думают, что введение Итератора делает Go Становится более сложным, поскольку реализация кода Итератора может повлиять на читаемость. Для тех, кто новичок в Go Итераториз Для разработчиков,Вы действительно можете чувствовать себя немного некомфортно. но,Go Чтобы упростить использование Итератоза, чиновник добавил: iter Сумка,исуществовать slices и maps В Сумке предусмотрено множество удобных функций для улучшения процесса разработки.

В целом введение Стандартный Итератор Унифицировал дизайн и использование Итераториз, решил проблему фрагментации и дополнительно оптимизировал. Go изэкосистема。

Что вы думаете об Итераторе? Добро пожаловать, чтобы оставить сообщение в области комментариев для обсуждения.

Ссылки

Range Over Function Types

Рекомендуем к прочтению

Вышла версия Go 1.23, вы должны знать эти важные обновления!

Go 1.23 Новая функция: Таймер и Ticker из Важная оптимизация

Go 1.23 Новая функция: ломтики, синхронизация и другие основные библиотеки были доработаны, чтобы значительно улучшить процесс разработки.

Привет,Я Чен Минён,Разработчик, который любит технологии и готов поделиться,Он также является энтузиастом открытого исходного кода.

Путь к успеху не переполнен. Вы заинтересованы в том, чтобы найти компаньона?

Следуйте за мной, добавляйте меня в друзья, учитесь и совершенствуйтесь вместе!

boy illustration
Учебное пособие по Jetpack Compose для начинающих, базовые элементы управления и макет
boy illustration
Код js веб-страницы, фон частицы, код спецэффектов
boy illustration
【новый! Суперподробное】Полное руководство по свойствам компонентов Figma.
boy illustration
🎉Обязательно к прочтению новичкам: полное руководство по написанию мини-программ WeChat с использованием программного обеспечения Cursor.
boy illustration
[Забавный проект Docker] VoceChat — еще одно приложение для мгновенного чата (IM)! Может быть встроен в любую веб-страницу!
boy illustration
Как реализовать переход по странице в HTML (html переходит на указанную страницу)
boy illustration
Как решить проблему зависания и низкой скорости при установке зависимостей с помощью npm. Существуют ли доступные источники npm, которые могут решить эту проблему?
boy illustration
Серия From Zero to Fun: Uni-App WeChat Payment Practice WeChat авторизует вход в систему и украшает страницу заказа, создает интерфейс заказа и инициирует запрос заказа
boy illustration
Серия uni-app: uni.navigateЧтобы передать скачок значения
boy illustration
Апплет WeChat настраивает верхнюю панель навигации и адаптируется к различным моделям.
boy illustration
JS-время конвертации
boy illustration
Обеспечьте бесперебойную работу ChromeDriver 125: советы по решению проблемы chromedriver.exe не найдены
boy illustration
Поле комментария, щелчок мышью, специальные эффекты, js-код
boy illustration
Объект массива перемещения объекта JS
boy illustration
Как открыть разрешение на позиционирование апплета WeChat_Как использовать WeChat для определения местонахождения друзей
boy illustration
Я даю вам два набора из 18 простых в использовании фонов холста Power BI, так что вам больше не придется возиться с цветами!
boy illustration
Получить текущее время в js_Как динамически отображать дату и время в js
boy illustration
Вам необходимо изучить сочетания клавиш vsCode для форматирования и организации кода, чтобы вам больше не приходилось настраивать формат вручную.
boy illustration
У ChatGPT большое обновление. Всего за 45 минут пресс-конференция показывает, что OpenAI сделал еще один шаг вперед.
boy illustration
Copilot облачной разработки — упрощение разработки
boy illustration
Микросборка xChatGPT с низким кодом, создание апплета чат-бота с искусственным интеллектом за пять шагов
boy illustration
CUDA Out of Memory: идеальное решение проблемы нехватки памяти CUDA
boy illustration
Анализ кластеризации отдельных ячеек, который должен освоить каждый&MarkerгенетическийВизуализация
boy illustration
vLLM: мощный инструмент для ускорения вывода ИИ
boy illustration
CodeGeeX: мощный инструмент генерации кода искусственного интеллекта, который можно использовать бесплатно в дополнение к второму пилоту.
boy illustration
Машинное обучение Реальный бой LightGBM + настройка параметров случайного поиска: точность 96,67%
boy illustration
Бесшовная интеграция, мгновенный интеллект [1]: платформа больших моделей Dify-LLM, интеграция без кодирования и встраивание в сторонние системы, более 42 тысяч звезд, чтобы стать свидетелями эксклюзивных интеллектуальных решений.
boy illustration
LM Studio для создания локальных больших моделей
boy illustration
Как определить количество слоев и нейронов скрытых слоев нейронной сети?
boy illustration
[Отслеживание целей] Подробное объяснение ByteTrack и детали кода