Go и интерфейсы
В Go интерфейсы представляют собой типы, определяющие наборы методов. Они используются для обеспечения полиморфного поведения объектов. В отличие от многих других языков программирования, в Go не требуется явное указание на то, что структура реализует интерфейс. Если структура имеет все методы, описанные в интерфейсе, то считается, что она его реализует.
Основные принципы работы интерфейсов:
Определение интерфейса: Интерфейс в Go описывается как набор методов. Структура или любой другой тип "реализует" интерфейс, если предоставляет реализацию всех методов, перечисленных в интерфейсе.
Полиморфизм: Интерфейсы позволяют переменным иметь различные типы значения во время выполнения программы, что обеспечивает полиморфизм. Это значит, что функция, принимающая интерфейс в качестве аргумента, может работать с любым типом, который реализует этот интерфейс.
Интерфейс{}: Пустой интерфейс interface{} не имеет методов и поэтому может представлять значение любого типа, включая встроенные типы данных. Он часто используется, когда точный тип данных заранее неизвестен.
package main
import "fmt"
// Определение интерфейса Animal
type Animal interface {
Speak() string
}
// Реализация интерфейса Animal для структуры Dog
type Dog struct {}
func (d Dog) Speak() string {
return "Woof!"
}
// Реализация интерфейса Animal для структуры Cat
type Cat struct {}
func (c Cat) Speak() string {
return "Meow"
}
// Функция, принимающая интерфейс Animal
func printAnimalSound(a Animal) {
fmt.Println(a.Speak())
}
func main() {
dog := Dog{}
cat := Cat{}
// Оба типа, Dog и Cat, реализуют интерфейс Animal
// поэтому printAnimalSound может с ними работать
printAnimalSound(dog) // Woof!
printAnimalSound(cat) // Meow
}
В этом примере Dog и Cat являются разными типами, которые реализуют интерфейс Animal, поскольку оба предоставляют метод Speak(). Функция printAnimalSound может принимать любой тип, реализующий Animal.
Подводные камни.
Производительность. Использование интерфейсов несколько снижает производительность по сравнению с работой с конкретными типами из-за необходимости решения типов во время выполнения. Давайте рассмотрим ситуацию, где производительность критична, и использование интерфейсов может влиять на производительность из-за динамического определения типов и вызова методов через интерфейсы. В таких случаях прямое использование конкретных типов может быть более эффективным.
package main
import (
"fmt"
"time"
)
// Animal интерфейс, который реализуют разные животные.
type Animal interface {
Say() string
}
// Dog структура, реализующая интерфейс Animal.
type Dog struct{}
func (d Dog) Say() string {
return "Woof!"
}
// функция, принимающая интерфейс Animal.
func makeNoise(animal Animal) {
fmt.Println(animal.Say())
}
// Функция, принимающая конкретный тип Dog.
func makeDogNoise(dog Dog) {
fmt.Println(dog.Say())
}
func main() {
dog := Dog{}
// Замер производительности при использовании интерфейса.
start_inter := time.Now()
for i := 0; i < 1000000; i++ {
makeNoise(dog)
}
result_iter := time.Since(start_inter)
// Замер производительности при использовании конкретного типа.
start := time.Now()
for i := 0; i < 1000000; i++ {
makeDogNoise(dog)
}
result_concrete := time.Since(start)
fmt.Printf("Using interface: %v\n", result_iter) // Using interface: 841.732596ms
fmt.Printf("Using concrete type: %v\n", result_concrete) // Using concrete type: 822.222233ms
}
В этом примере мы сравниваем время выполнения функций, которые работают с интерфейсом Animal и с конкретным типом Dog. Хотя разница в производительности может быть незначительной для малого количества вызовов, в высокопроизводительных системах или в системах с большим количеством вызовов эта разница может накапливаться.
Преимущества.
Полиморфизм: Интерфейсы позволяют писать функции и методы, которые могут работать с любым типом данных, реализующим интерфейс, не заботясь о конкретной реализации. Это означает, что вы можете легко заменить одну реализацию другой без изменения кода, который использует интерфейс.
Отделение интерфейса от реализации: Интерфейсы позволяют скрыть детали реализации за абстракцией. Это упрощает понимание кода, поскольку вам нужно сосредоточиться только на том, что делает код, а не как он это делает.
Упрощение тестирования: Использование интерфейсов упрощает написание модульных тестов. Вы можете легко создать "моки" или фиктивные реализации интерфейсов для тестирования, не завися от реализаций, которые могут требовать внешних зависимостей (например, базы данных).
Гибкость и расширяемость: Интерфейсы делают ваш код более гибким и легко расширяемым. Вы можете добавлять новые реализации интерфейсов без изменения существующего кода, что особенно полезно в больших и сложных системах.
Взаимозаменяемость компонентов: Поскольку компоненты системы общаются через интерфейсы, вы можете легко заменять одни компоненты другими, которые реализуют те же интерфейсы. Это особенно ценно для создания плагинов, расширений или для поддержки различных вариантов конфигурации системы.
В связи с недавними новостями, старый мем заиграл новыми красками
P.S. Для тех кто не в курсе, HP покупает Juniper.
Как подготовить машину к долгой поездке
Взять с собой побольше вкусняшек, запасное колесо и знак аварийной остановки. А что сделать еще — посмотрите в нашем чек-листе. Бонусом — маршруты для отдыха, которые можно проехать даже в плохую погоду.
Ответ на пост «Четкий расклад, как с языка снял»
Раньше рекламу в приложениях на Андроид можно было закрывать кнопкой "назад", потом эту возможность убрали и повесили е*#чий крестик в углу, потом крестик стал появляться с задержкой, а теперь крестиков надо нажать несколько и каждый с каким-то промежутком. Во где пи*#ры работают. А еще я тут месяц назад с Самсунга на Сяоми перешёл, так там вообще пи*#дец - реклама в штатных приложениях и на кране блокировки. 🤦♂️
Интерфейсы и абстрактные классы
Случилась со мной такая история ...
Недавно проходил собеседование на Java разработчика, как и на всех собеседованиях, задали вопрос про интерфейсы и абстрактные классы. Конечно, ответил, но все же решил перепроверить информацию на эту тему, так что здесь будет вся моя выдержка за это время
Давайте начнем с базовых ответов по теме интерфейс и абстрактный класс.
На вопрос: "Причем тут абстрактный класс?", отвечу так: "На собеседованиях эти вопросы идут рядом и в целом чем-то они похожи".
Итак, жил был абстрактный класс Василий. Объект этого класса создавать было нельзя, но Василий не унывал по этому поводу, ведь он содержит конструктор, может выполнять определенную логику в своих методах и иметь абстрактные методы (методы, не имеющие реализации, их нужно реализовать в классе наследнике), кроме этого Василий имел собственные поля с модификаторами доступа.
В те времена можно было наследовать много абстрактных классов и Василий не был исключением, наследовали его и всех его родственников. Но так получилось, что множественное наследование приводило к ошибкам наследования (одинаковые методы классов постоянно сорились) тогдв многие абстрактные классы иммигрировали в другие страны, а вместо них к Василию иммигрировали интерфейсы из public abstract Ифрики (нельзя наследовать много классов, но можно реализовывать много интерфейсов)
Таким образом Василий познакомился с интерфесом Амбалой. Амбала рассказал Василию, что он не содержит конструктора и реализовать его нельзя соответственно Методы интерфейса public и abstract по умолчанию
interface SomeInterface {
int SOME_THING = 11;
int foo();
}
Еще Амбала рассказал Василию, что содержит поле, но его поля только публичные, константные и статические, тогда как у Василия поля могут быть какими угодно. Но так было у предков Амбалы, тогда сам Амбала может содержать методы по умолчанию - медоты имеющие реализацию
interface SomeInterface {
default int foo() {
System.out.println("foo");
}
}
Также Амбала может иметь и статические методы, а обращаться к ним можно также как и к статическим методам класс
interface SomeInterface {
static int foo() {
System.out.println("foo");
}
}
public static void main(String[] args) {
SomeInterface.foo();
}
Шли годы и у Амбалы появились дети (jdk 9), они уже умели делать свои методы приватными и эти приватные методы могут быть как статическими так и нет.
Также к Амбале приехали родственники из Ифрики, оказалось, что они не содержат ни методов ни полей. "Как так получилось" - спросил Василий: "Что они умеют делать???".
Родственники рассказали Василию про таинственный полиморфизм: когда пустые интерфейсы используются, для пометки класса, реализующий этот интерфейс, чтобы использовать после этот класс в качестве реализации методов
interface Printable { }
class SomeClass implements Printable {
private int magicNumber = 3;
public int getMagicNumber() {
return magicNumber;
}
public String toString() {
return String.valueOf(magicNumber);
}
}
public class Main {
public static void main(String[] args) {
var someClass = new SomeClass();
print(someClass);
}
public static void print(Printable printable) {
System.out.println(printable);
}
}
Суть в том, что тема интерфейсов оказалось гораздо интереснее чем я думал.
P.S помимо прочего веду телеграмм-канал и буду рад если поддержите IT-литературу.
Дневник альфа тестирования ч.1
Всем привет. Этим летом жизнь перестала быть скучной, и вместо чтения очередных баянов на пикабу я увлекся одним стартапом.
Многие тут конечно уже слышали про него. Кто-то уже там, кто-то ждет релиза, а кто-то активно минусит любое упоминание капибары.
В любом случае мне кажется интересным то, как волшебнаяый силапендель пикабу заставил кучу людей вкладывать свои силы в новый стартап.
Поэтому выкладываю тут материал одного из пользователей о том, как проект взявший свое начало от пикабу, потихоньку приобретает самомстоятельно воплощение.
(Но ссылку на сам проект давать не буду, увы это по прежнему чревато, поблажки были сделаны для телеграмщиков, а не для тех кого волнуе судьба сообщества).
Дневник альфа тестирования ч.1
Решил сделать небольшой дневник альфа тестирования от, непосредственно, тестировщика, чтобы было представление в каком все состоянии, как всё продвигается и вообще в общем взаимодействие между командами.
Так же считаю, что пока на канале творилось безумие и рождались мемы, о разработчиках как-будто все забыли, а это неправильно.
Кто-то может знает, кто-то нет (если человек только попал на проект), капибара создаётся энтузиастами, главный посыл: юзеры создают все сами, донаты, пожертвования и прочее строго запрещены, таков был посыл изначально от @FreeDaSw и эта линия поддерживается по настоящее время
Откровенно говоря, заходил в альфу с большой опаской, так как опыт есть и обычно смотреть без слез невозможно на такие вещи.
Удивительно, но несмотря на баги, команда энтузиастов справилась на твёрдую пятёрку, сайт оказался приятным, минималистичным, но функционала для создания авторского контента в целом хватает. Но попробуем пойти по порядку.
Данная часть дневника будет обозреваться с мобильной версии и сравниваться будут мобильные версии.
Перво-наперво посмотрим дизайн:
Как уже говорилось дизайн минималистичный, но интуитивно понятный (так как команда никогда не скрывала, что делается своё пикабу с минусами и автобаном, буду сравнивать именно с ним)
Главная страница капибары
При заходе на сайт попадаем в "Тренды" которые являются аналогом "Горячего"
Сразу бросается в глаза то, что управление юзером и постами находится сверху и скрыто в отличии от пикабу где было все в шапочке
Главная страница пикабу
Скрытое меню пикабу
На капибаре не наблюдается в шапке переключение между категориями постов и при вызове скрытого меню мы попадаем сюда
Скрытое меню
По словам команды дизайна и фронтэнда уже разработан концепт, чтобы вынести самый главный функционал для просмотра постов в шапку
Так же было приятно, что пока идёт тестирование, команда активно вовлечена в предложения пользователей и даёт ответ на некоторые предложения пользователей.
Юзеры холиварят над размерами блока с картинками
Ответ команды дизайна
Так же команда дизайна по просьбе юзеров переработала визуально систему плюсов и минусов
Так было изначально
На это поменяли по просьбе команды тестирования
Дизайнер бдит за предложениями пользователей
Тестировщик опять все сломал фронт- и бэкенд в печали
Отчёты тестировщикам об исправлении найденных багов
В данный момент пользователей усиленно пытаются всё поломать, товарищу @Sergej_Serov удаётся это лучше всех
49.5 этого юзера неудержимы. Каким-то образом он смог сделать так, чтобы буквы уехали за пределы экрана, я повторить это не смог
Пользователь @Archi так соскучился по минусам, что во время теста чуть сам себя не отправил в автобан
Пока команда бэкенда где-то затаилась, но думаю во второй части дневника попробую охватить их работу.
Дневники будут выходить по мере возможности)
Я так и задумывал
Взято из телеграмма - Инкогнито