D-20. 预设更改DBMS 、bundle指令 、Gemfile && Reverse String II && III

开始Rails new前新手可以先做的。


Rails是允许客制生成框架内容的,下方即为指令,会出现很多客制化选项,今天稍微试玩一下。

$ rails new -h
-d, [--database=DATABASE]
# Preconfigure for selected database (options: mysql/postgresql/sqlite3/oracle/sqlserver/jdbcmysql/jdbcsqlite3/jdbcpostgresql/jdbc)
# Default: sqlite3

-d这个部分,就是选择要使用的DBMS,除非选择制作静态网页,不然不可能不使用DB
如果是练习包括会部署,一般免费服务器都有支援mysqlpostgresql

静态网页无连接资料库,使用者无法改变或建立资料,例如加入会员之类。
动态网页具有资料传输功能,需服务器与DB共同运作,才能有会员,建立修改或评论文章等工能。
两者可同时存在於同服务器,也可查询伪静态页面等相关文章。

-T

-T, [--skip-test], [--no-skip-test]                        # Skip test files
    [--skip-system-test], [--no-skip-system-test]          # Skip system test files

TDD是一件非常好的行为,但当rails generate时常常自动多出来的test files不一定需要,可以skip

rails new非常便宜。
就来试试

$ rails new your_project_name -d postgresql --skip-test
或
$ rails new your_project_name --database=postgresql -T

可以发现project/config/database.yml档案设定的DB是选用pgsql了,gem也有安装。rails generatecontroller或model也不会再出现test相关档案。

如果已经rails new才想改DB

rails db:system:change --to=postgresql
rails db:system:change --to=mysql
rails db:system:change --to=sqlite3
rails db:system:change --to=oracle
rails db:system:change --to=frontbase
rails db:system:change --to=sqlserver
rails db:system:change --to=jdbc

第一次帮自己的专案换DBMS还去复制贴上人家的/config/database.yml设定档,泪奔
这是我做这个纪录的原因....

记得

rails db:create                          # Creates the database from DATABASE_URL or...

rails db:migrate                         # Migrate the database (options: VERSION=x,...
#or
rails db:schema:load                     # Loads a database schema file (either db/s...

GemfileGemfile.lock

bundlebundle installbundle exec

拿到一个project先看README.md看看作者有没有提醒什麽,接着通常就会bundle
厉害一点的就bundle exec ......

$ gem list
#看b开头部分
bundler (2.2.6, default: 2.1.4)

bundlebundler这个gem的指令,默认执行install指令。所以基本上为了安装gembundlebundle install没有差别的。

但如果是要使用bundle install後面可以附加的指令时,或者说需要更符合自己的要求安装时则需用bundle install

#没去看,不会知道还有这麽多选项。菜鸟我玩过的也不多。
bundle install [--binstubs[=DIRECTORY]]
                 [--clean]
                 [--deployment]
                 [--frozen]
                 [--full-index]
                 [--gemfile=GEMFILE]
                 [--jobs=NUMBER]
                 [--local]
                 [--no-cache]
                 [--no-prune]
                 [--path PATH]
                 [--quiet]
                 [--redownload]  #即使本机有也且可用,还是要下载一次
                 [--retry=NUMBER] #家里网路不好,重试次数
                 [--shebang]
                 [--standalone[=GROUP[ GROUP...]]]
                 [--system]
                 [--trust-policy=POLICY]
                 [--with=GROUP[ GROUP...]]
                 [--without=GROUP[ GROUP...]]

bundle exec

Execute a command in the context of the bundle
毕竟bundle完通常就跑db:migrate所以bundle exec rake db:migrate不是更方便?

bundlebundler依照Gemfile档内要求安装所需gem,若本机没有则会下载,若Gemfile内没有特别标注PATH或版本号,例如'~> 6.1.3', '>= 6.1.3.2'bundler会协助下载专案中可用的最稳定的新版本。

bundle install则是对bundlerbundle时可以提出其他要求指令,例如bundle install --redownload,可以要求即使电脑里已有也要再下载安装一次。

补充:何为最稳定的新版本。
bundler会帮忙检查相容性,以及各种需要互相协助的gem是不是版本相符,如果指定版本号相冲或有问题,bundler都会做提醒及建议安装版本。如不指定版本号,会下载无beta的最新版本。

bundler 官网 https://bundler.io/

Gemfile是许愿池,Gemfile.lock是实现了哪些愿望。
可以看到bundle install甚至可以指定GemfileGemfile.lock才是真正纪录bundler安装了哪些gem资讯的地方。
Gemfile像是展示目前专案需有哪些gem协助运行,bundler会依照这份清单协助安装。

Gemfile长相

#告诉`bundler`去哪找
source 'https://rubygems.org'
git_source(:github) { |repo| "https://github.com/#{repo}.git" }
#Ruby版本号,用哪个版本开的就会记哪个版本,也可以new时选定。
ruby '2.7.3'
#这边开始是放产品区(production)所需的`gem`,习惯上不会出现单纯测试用或单纯开发用的gem。

group :development, :test do
#放开发与测试都需要的gem
end

group :development do
#习惯上只放单纯开发用gem
end

group :test do
#习惯上只放test用gem
end

Rails new还可以这麽做

RailsGuides
Rails Application Templates

To apply a template, you need to provide the Rails generator with the location of the template you wish to apply using the -m option. This can either be a path to a file or a URL.

$ rails new blog -m ~/template.rb
$ rails new blog -m http://example.com/template.rb

官网下有template.rb每一个部分的简单讲解。

是的Rails有可以客制化模板(Template),让你rails new时可以生出跟自己制作的Template一样的内容。网路上也有大神们分享自己的模板,其README.md档都有告知自己装了那些gem,如果只是简单想做一个不用反覆装gem的template.rb而已,可以尝试看看。


今天的
leetcode557.Reverse String III
leetcode541.Reverse String II

leetcode557.Reverse String III
题目连结:https://leetcode.com/problems/reverse-words-in-a-string-iii/
题目重点:单纯的字串拆分反转合并。 旋转 跳跃 我闭着眼

def reverse_words(s)

end

p reverse_words("Let's take LeetCode contest") #=> "s'teL ekat edoCteeL tsetnoc"
p reverse_words("God Ding") #=> "doG gniD"

看到反转,应该就直觉反应用reverse

#Array
 :022 > [1, 2, 3, 4, 5].reverse
 => [5, 4, 3, 2, 1]
 :032 > "Let's take LeetCode contest".split
 => ["Let's", "take", "LeetCode", "contest"]
 :034 > ["Let's", "take", "LeetCode", "contest"].map(&:reverse)
 => ["s'teL", "ekat", "edoCteeL", "tsetnoc"]

#单纯记得Array部分跟可以枚举元素反转应该就解得出了。
def reverse_words(s)
  s.split.map(&:reverse).join(" ")
end


#但是String用reverse还有一个特性。
:030 > "abcde".reverse
 => "edcba"
#字串中间有空格会这样
:031 > "abc def".reverse
 => "fed cba"
:032 > "Let's take LeetCode contest".reverse
 => "tsetnoc edoCteeL ekat s'teL"
:033 > "tsetnoc edoCteeL ekat s'teL".split
 => ["tsetnoc", "edoCteeL", "ekat", "s'teL"]
:034 > ["tsetnoc", "edoCteeL", "ekat", "s'teL"].reverse
 => ["s'teL", "ekat", "edoCteeL", "tsetnoc"]

def reverse_words(s)
  s.reverse.split.reverse.join(" ")
end

leetcode541.Reverse String II
题目连结:https://leetcode.com/problems/reverse-string-ii/
题目重点:看清楚那个k的意思,其实是每2*k一组,每一组的1与2对调。

def reverse_str(s, k)

end

p reverse_str("abcdefg", 2) #=> "bacdfeg"
p reverse_str("abcd", 2) #=> "bacd"

看不懂其实是2*k一组时时,II时III还难。
这题会用到StringArrayRange的隐藏特性。
虽然都解Easy但是看多了,越来越了解duck typing

:047 > str = "12345"
 => "12345"
 :048 > str[0..1] = str[0..1].reverse
 => "21"
 :049 > str
 => "21345"

了解後,就是看怎麽把字串分成2*k一组了。

:051 > "abcdefg".split("")
 => ["a", "b", "c", "d", "e", "f", "g"]
 :052 > "abcdefg".chars
 => ["a", "b", "c", "d", "e", "f", "g"]

~~对象是Array,找Array的方法吧。~~结果在Enumerable,需要枚举请找枚举!

each_slice(n) { ... } → nilclick to toggle source
each_slice(n) → an_enumerator
Iterates the given block for each slice of elements. If no block is given, returns an enumerator.

:053 > ["a", "b", "c", "d", "e", "f", "g"].each_slice(2*2).map(&:join)
 => ["abcd", "efg"]

OK!

:059 > ["abcd", "efg"].each{|str| str[0..2-1] = str[0..2-1].reverse}
 => ["bacd", "feg"]

整理後

def reverse_str(s, k)
  s_arr = s.chars.each_slice(2*k).map(&:join)
  s_arr.each{|str| str[0..k-1] = str[0..k-1].reverse}
  s_arr.join(" ")
end

今天提到的
1.bundlebundle installbundle exec
2.GemfileGemfile.lock差异
3.leetcode557.Reverse String III && leetcode541.Reverse String II


<<:  Android XML Parser

>>:  Day 10:Gson 资料解析

Unity与Photon的新手相遇旅途 | Day6-粒子效果应用范例

今天介绍两个粒子效果应用范例,一个是透过按键控制粒子效果生成以及删除,第二个是制作炸弹炸物体产生的效...

【Day 20】Go 基础语法

Python 改学 Go 之 基础语法小笔记 学习计画因为听到公司用 Go 而改为学 Go, 翻阅...

[重构倒数第27天] - 在 Vue 各种 CSS 的引入使用

前言 该系列是为了让看过Vue官方文件或学过Vue但是却不知道怎麽下手去重构现在有的网站而去规画的系...

Day12 探讨urls(2)

昨天跟大家介绍完 url 这个函式,不晓得大家有没有比较懂他的用法了呢?还是跟没看之前一样迷惘......

第25天 - 文件审核系统(3)_上传、下载的部分

今天上传、下载的程序码要参考昨天的文章(标签里的name值) https://ithelp.itho...