iOS架构师_架构模式(代理,block,通知,MVC,MVP,MVVM)

2023-11-01

1.什么是架构?

没有明确的定义,属于设计的一方面,没明确的把设计和架构进行区分,它可以小到类与类之间的交互,大到不同模块之间,以及不同业务之间的交互,都可以从架构的层面去理解它。

所有架构和设计模式的目的都是为了解耦合

2.基本的架构基础

案例需求:女朋友让男朋友去做饭,完了以后给抱抱

GirlFriend类
.h

#import <Foundation/Foundation.h>

@interface GirlFriend : NSObject
+ (instancetype)sharedInstance;

- (void)cookingIsDone;

- (void)begin;

@end

.m

#import "GirlFriend.h"
#import "BoyFriend.h"

@implementation GirlFriend
+ (instancetype)sharedInstance
{
    static id sharedInstance = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedInstance = [[self alloc] init];
    });
    return sharedInstance;
}

- (void)cookingIsDone {
    NSLog(@"给个爱的抱抱");
}

- (void)begin {
    [[BoyFriend sharedInstance] cooking];
}

@end

BoyFriend类

.h

#import <Foundation/Foundation.h>

@interface BoyFriend : NSObject

+ (instancetype)sharedInstance;

- (void)cooking;

@end

.m

#import "BoyFriend.h"
#import "GirlFriend.h"

@implementation BoyFriend

+ (instancetype)sharedInstance
{
    static id sharedInstance = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedInstance = [[self alloc] init];
    });
    return sharedInstance;
}

- (void)cooking {
    NSLog(@"baby,欧巴开始做饭了");
    [[GirlFriend sharedInstance] cookingIsDone];
}

@end

我们看上面的代码,可以看出,BoyFriend类和GirlFriend类是相互依赖的,那我们怎么解决这种依赖关系呢?三种方式代理和block以及通知

代理

BoyFriend.h

#import <Foundation/Foundation.h>

@protocol BoyFriendDelegate <NSObject>

- (void)boyFriendMakeCooking;

@end

@interface BoyFriend : NSObject

+ (instancetype)sharedInstance;

- (void)cooking;

@property (nonatomic, weak) id<BoyFriendDelegate> delegate;

@end

BoyFriend.m

#import "BoyFriend.h"
//#import "GirlFriend.h"

@implementation BoyFriend

+ (instancetype)sharedInstance
{
    static id sharedInstance = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedInstance = [[self alloc] init];
    });
    return sharedInstance;
}

- (void)cooking {
    NSLog(@"baby,欧巴开始做饭了");
//    [[GirlFriend sharedInstance] cookingIsDone];

    if (_delegate) {
        [_delegate boyFriendMakeCooking];
    }
}


@end

GirlFriend.h

#import <Foundation/Foundation.h>
#import "BoyFriend.h"

@interface GirlFriend : NSObject <BoyFriendDelegate>
+ (instancetype)sharedInstance;

- (void)cookingIsDone;

- (void)begin;

@end

GirlFriend.m

#import "GirlFriend.h"

@implementation GirlFriend
+ (instancetype)sharedInstance
{
    static id sharedInstance = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedInstance = [[self alloc] init];
    });
    return sharedInstance;
}

- (void)cookingIsDone {
    NSLog(@"给个爱的抱抱");
}

- (void)begin {
    [BoyFriend sharedInstance].delegate = self;

    [[BoyFriend sharedInstance] cooking];
}

- (void)boyFriendMakeCooking {
    NSLog(@"给个爱的抱抱");
}

@end

block

BoyFriend.h

#import <Foundation/Foundation.h>

@interface BoyFriend : NSObject

+ (instancetype)sharedInstance;

//- (void)cooking;

@property (nonatomic, copy) void(^myBolock)(NSString *);

- (void)cooking:(void(^)())success;

@end

BoyFriend.m

#import "BoyFriend.h"
//#import "GirlFriend.h"

@implementation BoyFriend

+ (instancetype)sharedInstance
{
    static id sharedInstance = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedInstance = [[self alloc] init];
    });
    return sharedInstance;
}

//- (void)cooking {
//    NSLog(@"baby,欧巴开始做饭了");
    [[GirlFriend sharedInstance] cookingIsDone];
//    
    if (_delegate) {
        [_delegate boyFriendMakeCooking];
    }
//}

- (void)cooking:(void (^)())success {
//    // 判断是否有这个block
//    if (self.myBolock) {
//        // 用参数的形式,把这信息,给block里面赋参数,传出去
//        self.myBolock(@"baby,欧巴开始做饭了");
//    }

    NSLog(@"baby,欧巴开始做饭了");
    // 调用这个block,把myBlock回调回去
    success(self.myBolock);
}

@end

GirlFriend.h

#import <Foundation/Foundation.h>
#import "BoyFriend.h"

@interface GirlFriend : NSObject
+ (instancetype)sharedInstance;

- (void)cookingIsDone;

- (void)begin;

@end

GirlFriend.m

#import "GirlFriend.h"

@implementation GirlFriend
+ (instancetype)sharedInstance
{
    static id sharedInstance = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedInstance = [[self alloc] init];
    });
    return sharedInstance;
}

- (void)begin {
//    // 声明这个block, 其实这一步可以省去的
//    [BoyFriend sharedInstance].myBolock = ^(NSString *str) {
//        NSLog(@"%@",str);
//    };
//    
    // 调用这个方法,里面对block进行声明
    [[BoyFriend sharedInstance] cooking:^{
        NSLog(@"给个爱的抱抱");
    }];
}

@end

block和代理是类似的方式,但是我们发现GirlFriend类中仍然需要引入BoyFriend的头文件,有没有办法,完全解除两个类的关系呢?苹果后期给出的通知就可以解决我们的问题。

通知

Header.h

#ifndef Header_h
#define Header_h

static NSString * const Notif_Begin = @"Notif_Begin";
static NSString * const Notif_cookingIsDone = @"Notif_cookingIsDone";

//#define Notif_Begin @"Notif_Begin"
//#define Notif_cookingIsDone @"Notif_cookingIsDone"

#endif /* Header_h */

GirlFriend.h

#import <Foundation/Foundation.h>
#import "Header.h"

@interface GirlFriend : NSObject
+ (instancetype)sharedInstance;

- (void)begin;

@end

GirlFriend.m

#import "GirlFriend.h"

@implementation GirlFriend
+ (instancetype)sharedInstance
{
    static id sharedInstance = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedInstance = [[self alloc] init];
    });
    return sharedInstance;
}

- (instancetype)init {
    self = [super init];
    if (self) {
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(cookingIsDone) name:Notif_cookingIsDone object:nil];
    }
    return self;
}
- (void)cookingIsDone {
    NSLog(@"给个爱的抱抱");
}

- (void)begin {
    [[NSNotificationCenter defaultCenter] postNotificationName:Notif_Begin object:nil];
}

@end

BoyFriend.h

#import <Foundation/Foundation.h>
#import "Header.h"

@interface BoyFriend : NSObject

+ (instancetype)sharedInstance;

- (void)addNotification;

@end

BoyFriend.m

#import "BoyFriend.h"

@implementation BoyFriend

+ (instancetype)sharedInstance
{
    static id sharedInstance = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedInstance = [[self alloc] init];
    });
    return sharedInstance;
}

- (void)addNotification {
    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(cooking) name:Notif_Begin object:nil];
}

- (void)cooking {
    NSLog(@"baby,欧巴开始做饭了");
    [[NSNotificationCenter defaultCenter] postNotificationName:Notif_cookingIsDone object:nil];
}
@end

3.MVC架构方式-面向对象

这里写图片描述

Model View Controller

Model

Paper.h

#import <Foundation/Foundation.h>

@interface Paper : NSObject
@property (nonatomic, strong) NSString *content;
@end

View

MVCView.h

#import <UIKit/UIKit.h>
#import "Paper.h"

@protocol MVCViewDelegate <NSObject>

- (void)onPrintBtnClick;

@end

@interface MVCView : UIView

- (void)printOnView:(Paper *)paper;

@property (nonatomic, weak) id<MVCViewDelegate> delegate;
@property (nonatomic, strong) UIButton *btnPrint;

@end

MVCView.m

#import "MVCView.h"

@implementation MVCView

- (void)printOnView:(Paper *)paper {
    NSLog(@"在MVCView中打印出的内容:%@",paper.content);
}

- (instancetype)init {
    self = [super init];
    if (self) {
        self.backgroundColor = [UIColor grayColor];

        self.btnPrint = [[UIButton alloc] initWithFrame:CGRectMake(100, 100, 100, 50)];
        [self.btnPrint setTitle:@"print" forState:UIControlStateNormal];
        [self.btnPrint addTarget:self action:@selector(onPrintClick) forControlEvents:UIControlEventTouchUpInside];
        [self addSubview:self.btnPrint];
    }
    return self;
}

- (void)onPrintClick {
//    NSLog(@"采集的事件");
    if (_delegate && [self.delegate respondsToSelector:@selector(onPrintBtnClick)]) {
        [_delegate onPrintBtnClick];
    }
}

@end

Controller
MVCViewController.h

#import <UIKit/UIKit.h>

@interface MVCViewController : UIViewController

@end

MVCViewController.m

#import "MVCViewController.h"
#import "MVCView.h"
#import "Paper.h"

@interface MVCViewController () <MVCViewDelegate>
@property (nonatomic, strong) MVCView *myView;
@property (nonatomic, strong) Paper *paper;

@end

@implementation MVCViewController

- (void)viewDidLoad {
    [super viewDidLoad];

    self.myView = [MVCView new];
    self.myView.delegate = self;
    self.myView.frame = self.view.bounds;
    [self.view addSubview:self.myView];

    self.paper = [Paper new];
    self.paper.content = @"mvc内容模式";

    [self.myView printOnView:self.paper];

}

// 实现了代理方法
- (void)onPrintBtnClick {

    int rand = arc4random_uniform(10);
    _paper.content = [NSString stringWithFormat:@"改变的数据 %d",rand+1];

    [self.myView printOnView:self.paper];
}

@end

MVC架构方式其实就是把数据,视图,控制器三者分离,是最基础的设计模式,MVP和MVVM都是在其基础上衍生出来的。

4.MVP架构方式-面向接口

这里写图片描述
Model View Presenter

Controller中的所有逻辑都放在Presenter中实现,与MVC不同的是Model与View是没有任何联系的,都是通过Presenter来交互

代码示例:

这里写图片描述
注意:MVP的架构方式还是需要Controller的,它只不过是把Controller中的逻辑放在Presenter中去实现

Model

#import <Foundation/Foundation.h>

@interface MVPModel : NSObject
@property (nonatomic, strong) NSString *content;

@end

View

MVPView.h

#import <UIKit/UIKit.h>

@protocol MVPViewDelegate <NSObject>

- (void)viewShowBtnClick;

@end

@interface MVPView : UIView
@property (nonatomic, weak) id<MVPViewDelegate> delegate;

- (void)showView:(NSString *)content;
@end

MVPView.m

#import "MVPView.h"

@interface MVPView ()
@property (nonatomic, strong) UILabel *label;
@property (nonatomic, strong) UIButton *btnPrint;
@end

@implementation MVPView

- (instancetype)init
{
    self = [super init];
    if (self) {

        self.backgroundColor = [UIColor grayColor];
        self.label = [[UILabel alloc] initWithFrame:CGRectMake(0, 100, 300, 30)];

        self.label.textAlignment = NSTextAlignmentCenter;

        self.label.textColor = [UIColor blackColor];

        [self addSubview:self.label];

        self.btnPrint = [[UIButton alloc] initWithFrame:CGRectMake(100, 200, 100, 50)];

        [self.btnPrint setTitle:@"来点我呀" forState:UIControlStateNormal];

        [self.btnPrint addTarget:self action:@selector(onPrintClick) forControlEvents:UIControlEventTouchUpInside];


        [self addSubview:self.btnPrint];

    }
    return self;
}

- (void)showView:(NSString *)content {
    self.label.text = content;
}

- (void)onPrintClick {
    if (_delegate && [_delegate respondsToSelector:@selector(viewShowBtnClick)]) {
        [_delegate viewShowBtnClick];
    }
}

创建继承自NSObject的类Presenter
Presenter.h

#import <Foundation/Foundation.h>
#import "MVPModel.h"
#import "MVPView.h"

@interface Presenter : NSObject <MVPViewDelegate>
@property (nonatomic, strong) MVPModel *model;
@property (nonatomic, strong) MVPView *view;

- (void)usageLogic;
@end

Presenter.m

#import "Presenter.h"

@implementation Presenter

- (void)usageLogic {
    NSString *contentStr = self.model.content;

    self.view.delegate = self;
    [self.view showView:contentStr];
}

- (void)viewShowBtnClick {
    int num = arc4random_uniform(20);
    self.model.content = [NSString stringWithFormat:@"mvp--%d-",num];

    [_view showView:_model.content];
}
@end

Controller
MVPViewController.m

#import "MVPViewController.h"
#import "Presenter.h"
#import "MVPModel.h"
#import "MVPView.h"

@interface MVPViewController () 
@property (nonatomic, strong) Presenter *presenter;
@property (nonatomic, strong) MVPView  *mvpView;
@property (nonatomic, strong) MVPModel *mvpModel;
@end

@implementation MVPViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    // Do any additional setup after loading the view.

    _presenter = [[Presenter alloc] init];

    _mvpView = [[MVPView alloc] init];
    _mvpView.frame = self.view.bounds;
    [self.view addSubview:_mvpView];

    _mvpModel = [MVPModel new];
    _mvpModel.content = @"MVP的模式";
    // model还没赋值
    _presenter.model = _mvpModel;
    _presenter.view = _mvpView;
    [_presenter usageLogic];

}

@end

5.MVVM架构方式-响应式编程

这里写图片描述

这里写图片描述

MVVMModel.h

#import <Foundation/Foundation.h>

@interface MVVMModel : NSObject
@property (nonatomic, copy) NSString *content;
@end

MVVMView.h


#import <UIKit/UIKit.h>
#import "MVVMViewModel.h"


@interface MVVMView : UIView
@property (nonatomic, strong) UILabel *labelContent;
@property (nonatomic, strong) UIButton *btnPrint;
@property (nonatomic, strong) MVVMViewModel *vm;

- (void)showView:(MVVMViewModel *)viewModel;

@end

MVVMView.m

#import "MVVMView.h"

@implementation MVVMView

- (instancetype)init
{
    self = [super init];
    if (self) {

        self.backgroundColor = [UIColor grayColor];
        self.labelContent = [[UILabel alloc] initWithFrame:CGRectMake(0, 100, 300, 30)];

        self.labelContent.textAlignment = NSTextAlignmentCenter;

        self.labelContent.textColor = [UIColor blackColor];

        [self addSubview:self.labelContent];

        self.btnPrint = [[UIButton alloc] initWithFrame:CGRectMake(100, 200, 100, 50)];

        [self.btnPrint setTitle:@"来点我呀---" forState:UIControlStateNormal];

        [self.btnPrint addTarget:self action:@selector(onPrintClick) forControlEvents:UIControlEventTouchUpInside];


        [self addSubview:self.btnPrint];

    }
    return self;
}

- (void)onPrintClick {
    [self.vm viewModelPrintClick];
}

- (void)showView:(MVVMViewModel *)viewModel {
    self.vm = viewModel;
    [self.KVOController observe:viewModel keyPath:@"contentStr" options:NSKeyValueObservingOptionInitial | NSKeyValueObservingOptionNew block:^(id  _Nullable observer, id  _Nonnull object, NSDictionary<NSKeyValueChangeKey,id> * _Nonnull change) {
        _labelContent.text = change[NSKeyValueChangeNewKey];
    }];
}

@end

MVVMViewModel.h

#import <Foundation/Foundation.h>
#import "FBKVOController.h"
#import "NSObject+FBKVOController.h"
#import "MVVMModel.h"

@interface MVVMViewModel : NSObject

@property (nonatomic, copy) NSString *contentStr;

- (void)setWithModel:(MVVMModel *)model;

- (void)viewModelPrintClick;
@end

MVVMViewModel.m

#import "MVVMViewModel.h"

@interface MVVMViewModel ()
@property (nonatomic, strong) MVVMModel *model;
@end

@implementation MVVMViewModel
- (void)setWithModel:(MVVMModel *)model {
    self.model = model;
    self.contentStr = self.model.content;
}

- (void)viewModelPrintClick {
    self.model.content = @"MVVMModel";

    int num = arc4random_uniform(20);
    self.model.content = [NSString stringWithFormat:@"%d",num];
    self.contentStr = self.model.content;
}

@end

MVVMController.m

#import "MVVMController.h"
#import "MVVMModel.h"
#import "MVVMView.h"
#import "MVVMViewModel.h"

@interface MVVMController ()
@property (nonatomic, strong) MVVMView *mvvmView;
@property (nonatomic, strong) MVVMModel *model;
@property (nonatomic, strong) MVVMViewModel *viewModel;
@end

@implementation MVVMController

- (void)viewDidLoad {
    [super viewDidLoad];
    // Do any additional setup after loading the view.
    self.model = [[MVVMModel alloc] init];
    self.model.content = @"MVVM架构模式";

    _viewModel = [MVVMViewModel new];

    _mvvmView = [MVVMView new];
    _mvvmView.frame = self.view.bounds;
    [self.view addSubview:_mvvmView];

    [_viewModel setWithModel:_model];
    [_mvvmView showView:_viewModel];

}

@end

这里写图片描述

注意:FBKVOController是个使用KVO的小框架,可以去gitHub上去找。我们在这使用KVO的模式来使ViewModel和View进行数据交互。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

iOS架构师_架构模式(代理,block,通知,MVC,MVP,MVVM) 的相关文章

  • iOS进阶_密码学进阶(一.对称加密算法简介)

    加密算法 HASH 散列函数 不可逆 密码 识别 文件 识别 以下两种加密算法 都是可逆的 明文 gt 加密 gt 密文 密文 gt 解密 gt 明文 对称加密 传统加密算法 加密和解密使用同一个 密钥 密钥的保密工作就非常的重要 密钥会定
  • iOS进阶_密码学进阶(二.对称加密算法代码演练)

    对称加密算法代码演练 终端测试指令 DES ECB 加密 echo n hello openssl enc des ecb K 616263 nosalt base64 DES CBC 加密 echo n hello openssl enc
  • iOS架构师_观察者模式

    定义 观察者模式 有时又被称为模型 视图 View 模式 源 收听者 Listener 模式或从属者模式 一个目标物件管理所有相依于它的观察者物件 并且在它本身的状态改变时主动发出通知 这通常透过呼叫各观察者所提供的方法来实现 此种模式通常
  • iOS架构师_UML建模语言

    UML UML统称建模语言 面向对象软件的表转化建模语言 包含Booch MOT OOSE 工具 StarUML 时序图
  • iOS进阶_GCD(二.GCD串行队列&并发队列)

    GCD 核心概念 将任务添加到队列 指定任务执行的方法 任务 使用block封装 block 就是一个提前准备好的代码块 在需要的时候执行 队列 负责调度任务 串行队列 一个接一个的调度任务 并发队列 可以同时调度多个任务 任务执行函数 任
  • iOS进阶—Runtime基础

    iOS进阶 目录 GitHub参考 RunTime 基础 一个程序的执行过程 大概就是代码 gt 编译链接 gt 执行 C语言 import
  • iOS架构-组件化(项目实战-项目首页架构)

    UI架构设计 设计模式 外观模式 代理模式 适配器模式 adapter 注意 一版本只是搭建结构 一 1 0 Tab搭建 二 1 1 新增UICollectionView 主页 gt 整体设计基于 gt UICollectionView 滑
  • iOS开发_HOOK

    我们在使用NSURLRequest时 传入请求地址URL 但是如果URL中有中文的话 我们会发现NSURLRequest的请求地址会报空 void viewDidLoad super viewDidLoad NSURL url NSURL
  • iOS架构师_架构模式(代理,block,通知,MVC,MVP,MVVM)

    1 什么是架构 没有明确的定义 属于设计的一方面 没明确的把设计和架构进行区分 它可以小到类与类之间的交互 大到不同模块之间 以及不同业务之间的交互 都可以从架构的层面去理解它 所有架构和设计模式的目的都是为了解耦合 2 基本的架构基础 案
  • iOS核心动画CoreAnimation系统进阶(赛贝尔曲线-菜单侧滑动画拆分动画详解)

    我们知道动画是基于绘制的 多次绘制贝塞尔的过程就会形成动画 流畅的动画效果会给用户带来不一样的使用体验 下面我们就让App开发中经常使用到的侧滑动画进行拆分详解 效果图如下 为侧滑动画封装一个slideMenuView 绘制侧滑动画需要下面
  • iOS进阶_多线程(二.线程间的状态)

    ViewController m 004 NSThread状态 Created by mac on 2018 4 27 Copyright 2018年 mac All rights reserved import ViewControlle
  • iOS架构-组件化(Carthage管理工具)

    一 Carthage项目管理工具使用 Step 1 安装 更新Homebrew工具 1 usr bin ruby e curl fsSL https raw githubusercontent com Homebrew install ma
  • iOS自动化布局-AutoLayout约束优先级

    约束的优先级 AutoLayout添加的约束中也有优先级 Priority 优先级的数值1 1000 分为两种情况 一种情况是我们经常添加的各种约束 默认值1000 最大值 优先执行 条件允许的话系统会自动满足我们的约束需求 第二种就是固有
  • iOS开发之ReactiveCocoa框架(RAC)第五篇队列与高级函数

    h文件 import ViewController h import ReactiveCocoa interface ViewController end implementation ViewController void viewDid
  • iOS开发之Runtime运行时机制

    摘要 Objective C是基于C加入了面向对象特性和消息转发机制的动态语言 除编译器之外 还需用Runtime系统来动态创建类和对象 进行消息发送和转发 作者通过分析Apple开源的Runtime代码来深入理解OC的Runtime机制
  • iOS进阶_Log分类打印日志自动转换中文

    description方法是NSObject类的一个实例方法 因此所有的Object C对象都有description方法 description方法返回的永远是字符串 对于一个Person类 如果没有重写description方法 NSL
  • iOS开发 多线程的高级应用-信号量semaphore

    在iOS开发的道路上 多线程的重要性不言而喻 大部分我们都停留在基础的使用上面 缺乏高级应用 缺乏提升 是因为我们面对他太少 复杂的事情重复做 复杂的事务基础化 差距就是这样拉开了 言归正传 今天讲讲GCD的高级应用之信号量篇 一 信号量的
  • iOS进阶_NSURLSession(二.断点续传)

    断点续传 从上一篇文章中 我们了解了使用NSURLSession进行文件下载 我们在其基础上继续探索NSURLSession的断点续传 在NSURLSession中 我们使用reumeData来存储下载的数据进度 import ViewCo
  • iOS进阶_kvc使用注意事项

    细节1 我们在项目中使用kvc 在设置model属性的时候 注意尽量不要使用基本数据类型 实例 数据模拟 注意age是null类型的 Person h import
  • iOS架构-组件化(项目框架搭建2)

    静态库引用静态库 如果像上图一样 直接在业务层组件引用数据层组件的文件 则会报错 因为组件之间没有建立引用关系 如下图 静态库如何引用Pods第三方库 拷贝Podfile文件到项目 打开终端执行pad install 直接引用Pod下面的Y

随机推荐

  • 金蝶EAS-BOS二开详细过程

    我们在做金蝶的项目时 经常会要求更改其项目本身的代码 但是它的代码都被封装在jar包中 我们应该怎么做呢 将要二开的单据实体或者facade 复制到我们的本地项目中 选中你要修改的具体实体或者facade 右键点击复制 重命名 复制到我们的
  • 配置Hadoop集群+WordCount案例

    配置Hadoop集群 配置环境变量 etc profile export HADOOP HOME bigData hadoop 2 8 0 export PATH P A T H PATH PATH HADOOP
  • cannot read property ‘line‘ of undefined

    环境 vite vue3 ts 这个问题的点还挺不明显的 翻了翻代码修改记录 发现是漏了结尾的 lt style gt 标签 做好本地代码管理真的很重要
  • gradle 两种更新方法

    第一种 Android studio更新 第一步 在你所在项目文件夹下 你项目根目录gradlewrappergradle wrapper properties 替换 distributionUrl https services gradl
  • 【算法/剑指Offer】地上有一个m行和n列的方格。一个机器人从坐标0,0的格子开始移动,每一次只能向左,右,上,下四个方向移动一格,但是不能进入行坐标和列坐标的数位之和大于k的格子。

    题目描述 地上有一个m行和n列的方格 一个机器人从坐标0 0的格子开始移动 每一次只能向左 右 上 下四个方向移动一格 但是不能进入行坐标和列坐标的数位之和大于k的格子 例如 当k为18时 机器人能够进入方格 35 37 因为3 5 3 7
  • java螺旋数组

    1 程序设计题 对于一个 n 行 m 列的表格 我们可以使用螺旋的方式给表格依次填上正整数 我们称填好的表格为一个螺旋矩阵 例如 一个 4 行 5 列的螺旋矩阵如下 1 2 3 4 5 14 15 16 17 6 13 20 19 18 7
  • jquery 等待3秒钟执行函数

    setTimeout function div2 hide 3000
  • CF1249B2 Books Exchange (hard version) 题解

    题目大意 共 q q q 组询问 对于每一组询问有长度为 n n n 的序列 p p
  • Linux进程内核栈

    进程创建的时候Linux内核会创建内核栈 arm手册也要求内核态有单独的栈 如应用进程在用户态通过系统调用陷入内核态的时候 上下文信息 如cpu寄存器 需要有个地方保存 如此 从内核态切换回用户态时候 能继续从系统调用之后的代码开始执行 这
  • JSON数据采集(采集JSON格式数据)

    如果想要采集JSON格式数据的网页怎么办 Json数据格式的页面 常出现于以下场景 1 滚动加载页面采集 瀑布流加载采集 2 网址没有变化的页面采集 3 采集点击加载更多的页面 这些页面我们都可以尝试使用简数采集器来实现JSON数据采集 1
  • Java 1.5, 1.6, 1.7, 1.8的区别

    对于很多刚接触java语言的初学者来说 要了解一门语言 最好的方式就是要能从基础的版本进行了解 升级的过程 以及升级的新特性 这样才能循序渐进的学好一门语言 今天先为大家介绍一下JDK1 5版本到JDK1 7版本的特性 希望能给予帮助 JD
  • MybatisPlus自定义sql多表关联分页条件查询

    MybatisPlus自定义sql多表关联分页条件查询 mp封装了crud但是对应复杂sql还是需要自己定义 网上对于多表分页查询的mp描述不是很清楚 我在这里重新写一篇文章 1 数据库准备 需要实现的sql是两表关联条件查询 select
  • MeterSphere 至善篇

    简介 MeterSphere 是一站式开源持续测试平台 涵盖测试跟踪 接口测试 UI 测试和性能测试等功能 全面兼容 JMeter Selenium 等主流开源标准 有效助力开发和测试团队充分利用云弹性进行高度可扩展的自动化测试 加速高质量
  • 自动适配手机网页 适配手机的网站网页 网页自动适配

    自动适配手机网页 适配手机的网站网页 网页自动适配 Category xy309 Time 2012 11 21 8 54 26 点击 14次 Source 兴移 允许网页宽度自动调整 自适应网页设计 到底是怎么做到的 其实并不难 首先 在
  • (面试题)如何解决MySQL慢查询

    慢查询出现原因以及解决方法 扫描多余的数据 避免使用select from xxx 跨多表扫描数据 可以减少join 并适当反范式化 增加冗余数据 以空间换时间 索引没有建立 索引优化不当 或未应用到最佳索引 联合索引使用最左匹配 CREA
  • 【无标题】UE5从百度盘下载UEC++项目到本地所遇到的一些问题和解决方法

    从百度盘里下载UEC 项目到自己的电脑 如果直接用VS打开C 会报打不开源文件等错误 如下图所示 解决方法 删除 图中用红线框的文件夹 若是VS 版本不同也可以把 sln 文件删除 删除后再生成c 项目 若是打开VS 编译是出现以下弹窗 则
  • 一级指针

    一级指针是一种指针 它指向一块内存地址 这块内存中存储的是另一个变量的内存地址 使用一级指针 你可以间接访问到这个变量 在 C C 中 可以使用一级指针来动态分配内存 改变函数参数的值 或者通过指针传递数组 下面是一个使用一级指针的例子 i
  • Java基础 时间相关类小结[Timestamp,Date,Calendar]

    Java基础 时间相关类 Timestamp Date Calendar 前言 一 Timestamp 时间戳 二 Date 日期 三 Calendar 日历 四 Timestamp Date Calendar的转换 五 日期之间的比较 前
  • 计算机组成原理学习笔记——六、总线

    文章目录 计算机组成原理学习笔记 六 CPU总线 6 1 总线概述 6 2 总线仲裁 6 3 总线操作和定时 6 4 总线标准 小结 计算机组成原理学习笔记 六 CPU总线 6 1 总线概述 总线的猝发传送方式 一个总线周期内传输存储地址连
  • iOS架构师_架构模式(代理,block,通知,MVC,MVP,MVVM)

    1 什么是架构 没有明确的定义 属于设计的一方面 没明确的把设计和架构进行区分 它可以小到类与类之间的交互 大到不同模块之间 以及不同业务之间的交互 都可以从架构的层面去理解它 所有架构和设计模式的目的都是为了解耦合 2 基本的架构基础 案